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

#include <google/protobuf/test_util.h>
#include <google/protobuf/unittest.pb.h>
#include <google/protobuf/arena.h>
#include <google/protobuf/descriptor.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);

  std::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);

  std::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);

  std::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);

  std::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);
  std::unique_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);
  std::unique_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, SetAllocatedMessageOnArenaTest) {
  unittest::TestAllTypes from_message1;
  unittest::TestAllTypes from_message2;
  ::google::protobuf::Arena arena;
  unittest::TestAllTypes* to_message =
      ::google::protobuf::Arena::CreateMessage<unittest::TestAllTypes>(&arena);
  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, SetAllocatedExtensionMessageOnArenaTest) {
  ::google::protobuf::Arena arena;
  unittest::TestAllExtensions* to_message =
      ::google::protobuf::Arena::CreateMessage<unittest::TestAllExtensions>(&arena);
  unittest::TestAllExtensions from_message1;
  unittest::TestAllExtensions from_message2;
  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();
  std::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")));

  message.clear_foo();
  message.clear_bar();
  TestUtil::ExpectOneofClear(message);
}

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, SetAllocatedOneofMessageOnArenaTest) {
  unittest::TestOneof2 from_message1;
  unittest::TestOneof2 from_message2;
  ::google::protobuf::Arena arena;
  unittest::TestOneof2* to_message =
      ::google::protobuf::Arena::CreateMessage<unittest::TestOneof2>(&arena);
  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);
  // Since sub_message is arena allocated, releasing it results in copying it
  // into new heap-allocated memory.
  EXPECT_NE(&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);
  // Since sub_message2 is arena allocated, releasing it results in copying it
  // into new heap-allocated memory.
  EXPECT_NE(&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
