// Copyright 2018 Google Inc.
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//      http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.
//
////////////////////////////////////////////////////////////////////////////////

#include "tink/subtle/xchacha20_poly1305_boringssl.h"

#include <string>
#include <vector>

#include "gtest/gtest.h"
#include "absl/strings/str_cat.h"
#include "openssl/err.h"
#include "tink/util/status.h"
#include "tink/util/statusor.h"
#include "tink/util/test_matchers.h"
#include "tink/util/test_util.h"

namespace crypto {
namespace tink {
namespace subtle {
namespace {

using ::crypto::tink::test::StatusIs;

TEST(XChacha20Poly1305BoringSslTest, TestBasic) {
  if (kUseOnlyFips) {
    GTEST_SKIP() << "Not supported in FIPS-only mode";
  }

  util::SecretData key = util::SecretDataFromStringView(test::HexDecodeOrDie(
      "000102030405060708090a0b0c0d0e0f000102030405060708090a0b0c0d0e0f"));
  auto res = XChacha20Poly1305BoringSsl::New(key);
  EXPECT_TRUE(res.ok()) << res.status();
  auto cipher = std::move(res.ValueOrDie());
  std::string message = "Some data to encrypt.";
  std::string aad = "Some data to authenticate.";
  auto ct = cipher->Encrypt(message, aad);
  EXPECT_TRUE(ct.ok()) << ct.status();
  EXPECT_EQ(ct.ValueOrDie().size(),
            message.size() + 24 /* nonce */ + 16 /* tag */);
  auto pt = cipher->Decrypt(ct.ValueOrDie(), aad);
  EXPECT_TRUE(pt.ok()) << pt.status();
  EXPECT_EQ(pt.ValueOrDie(), message);
}

TEST(XChacha20Poly1305BoringSslTest, TestModification) {
  if (kUseOnlyFips) {
    GTEST_SKIP() << "Not supported in FIPS-only mode";
  }

  util::SecretData key = util::SecretDataFromStringView(test::HexDecodeOrDie(
      "000102030405060708090a0b0c0d0e0f000102030405060708090a0b0c0d0e0f"));
  auto cipher = std::move(XChacha20Poly1305BoringSsl::New(key).ValueOrDie());
  std::string message = "Some data to encrypt.";
  std::string aad = "Some data to authenticate.";
  std::string ct = cipher->Encrypt(message, aad).ValueOrDie();
  EXPECT_TRUE(cipher->Decrypt(ct, aad).ok());
  // Modify the ciphertext
  for (size_t i = 0; i < ct.size() * 8; i++) {
    std::string modified_ct = ct;
    modified_ct[i / 8] ^= 1 << (i % 8);
    EXPECT_FALSE(cipher->Decrypt(modified_ct, aad).ok()) << i;
  }
  // Modify the additional data
  for (size_t i = 0; i < aad.size() * 8; i++) {
    std::string modified_aad = aad;
    modified_aad[i / 8] ^= 1 << (i % 8);
    auto decrypted = cipher->Decrypt(ct, modified_aad);
    EXPECT_FALSE(decrypted.ok()) << i << " pt:" << decrypted.ValueOrDie();
  }
  // Truncate the ciphertext
  for (size_t i = 0; i < ct.size(); i++) {
    std::string truncated_ct(ct, 0, i);
    EXPECT_FALSE(cipher->Decrypt(truncated_ct, aad).ok()) << i;
  }
}

void TestDecryptWithEmptyAad(crypto::tink::Aead* cipher, absl::string_view ct,
                             absl::string_view message) {
  if (kUseOnlyFips) {
    GTEST_SKIP() << "Not supported in FIPS-only mode";
  }

  {  // AAD is a null string_view.
    const absl::string_view aad;
    auto pt_or_status = cipher->Decrypt(ct, aad);
    EXPECT_TRUE(pt_or_status.ok()) << pt_or_status.status();
    auto pt = pt_or_status.ValueOrDie();
    EXPECT_EQ(message, pt);
  }
  {  // AAD is a an empty string.
    auto pt_or_status = cipher->Decrypt(ct, "");
    EXPECT_TRUE(pt_or_status.ok()) << pt_or_status.status();
    auto pt = pt_or_status.ValueOrDie();
    EXPECT_EQ(message, pt);
  }
  {  // AAD is a nullptr.
    auto pt_or_status = cipher->Decrypt(ct, nullptr);
    EXPECT_TRUE(pt_or_status.ok()) << pt_or_status.status();
    auto pt = pt_or_status.ValueOrDie();
    EXPECT_EQ(message, pt);
  }
}

TEST(XChacha20Poly1305BoringSslTest, TestAadEmptyVersusNullStringView) {
  if (kUseOnlyFips) {
    GTEST_SKIP() << "Not supported in FIPS-only mode";
  }

  const util::SecretData key =
      util::SecretDataFromStringView(test::HexDecodeOrDie(
          "000102030405060708090a0b0c0d0e0f000102030405060708090a0b0c0d0e0f"));
  auto cipher = std::move(XChacha20Poly1305BoringSsl::New(key).ValueOrDie());
  {  // AAD is a null string_view.
    const std::string message = "Some data to encrypt.";
    const absl::string_view aad;
    auto ct_or_status = cipher->Encrypt(message, aad);
    EXPECT_TRUE(ct_or_status.ok()) << ct_or_status.status();
    auto ct = ct_or_status.ValueOrDie();
    TestDecryptWithEmptyAad(cipher.get(), ct, message);
  }
  {  // AAD is a an empty string.
    const std::string message = "Some data to encrypt.";
    auto ct_or_status = cipher->Encrypt(message, "");
    EXPECT_TRUE(ct_or_status.ok()) << ct_or_status.status();
    auto ct = ct_or_status.ValueOrDie();
    TestDecryptWithEmptyAad(cipher.get(), ct, message);
  }
  {  // AAD is a nullptr.
    const std::string message = "Some data to encrypt.";
    auto ct_or_status = cipher->Encrypt(message, nullptr);
    EXPECT_TRUE(ct_or_status.ok()) << ct_or_status.status();
    auto ct = ct_or_status.ValueOrDie();
    TestDecryptWithEmptyAad(cipher.get(), ct, message);
  }
}

TEST(XChacha20Poly1305BoringSslTest, TestMessageEmptyVersusNullStringView) {
  if (kUseOnlyFips) {
    GTEST_SKIP() << "Not supported in FIPS-only mode";
  }

  const util::SecretData key =
      util::SecretDataFromStringView(test::HexDecodeOrDie(
          "000102030405060708090a0b0c0d0e0f000102030405060708090a0b0c0d0e0f"));
  auto cipher = std::move(XChacha20Poly1305BoringSsl::New(key).ValueOrDie());
  const std::string aad = "Some data to authenticate.";
  {  // Message is a null string_view.
    const absl::string_view message;
    auto ct_or_status = cipher->Encrypt(message, aad);
    EXPECT_TRUE(ct_or_status.ok());
    auto ct = ct_or_status.ValueOrDie();
    auto pt_or_status = cipher->Decrypt(ct, aad);
    EXPECT_TRUE(pt_or_status.ok()) << pt_or_status.status();
    auto pt = pt_or_status.ValueOrDie();
    EXPECT_EQ("", pt);
  }
  {  // Message is an empty string.
    const std::string message = "";
    auto ct_or_status = cipher->Encrypt(message, aad);
    EXPECT_TRUE(ct_or_status.ok());
    auto ct = ct_or_status.ValueOrDie();
    auto pt_or_status = cipher->Decrypt(ct, aad);
    EXPECT_TRUE(pt_or_status.ok()) << pt_or_status.status();
    auto pt = pt_or_status.ValueOrDie();
    EXPECT_EQ("", pt);
  }
  {  // Message is a nullptr.
    auto ct_or_status = cipher->Encrypt(nullptr, aad);
    EXPECT_TRUE(ct_or_status.ok());
    auto ct = ct_or_status.ValueOrDie();
    auto pt_or_status = cipher->Decrypt(ct, aad);
    EXPECT_TRUE(pt_or_status.ok()) << pt_or_status.status();
    auto pt = pt_or_status.ValueOrDie();
    EXPECT_EQ("", pt);
  }
}

TEST(XChacha20Poly1305BoringSslTest, TestBothMessageAndAadEmpty) {
  if (kUseOnlyFips) {
    GTEST_SKIP() << "Not supported in FIPS-only mode";
  }

  const util::SecretData key =
      util::SecretDataFromStringView(test::HexDecodeOrDie(
          "000102030405060708090a0b0c0d0e0f000102030405060708090a0b0c0d0e0f"));
  auto cipher = std::move(XChacha20Poly1305BoringSsl::New(key).ValueOrDie());
  {  // Both are null string_view.
    const absl::string_view message;
    const absl::string_view aad;
    auto ct_or_status = cipher->Encrypt(message, aad);
    EXPECT_TRUE(ct_or_status.ok());
    auto ct = ct_or_status.ValueOrDie();
    auto pt_or_status = cipher->Decrypt(ct, aad);
    EXPECT_TRUE(pt_or_status.ok()) << pt_or_status.status();
    auto pt = pt_or_status.ValueOrDie();
    EXPECT_EQ("", pt);
  }
  {  // Both are empty string.
    const std::string message = "";
    const std::string aad = "";
    auto ct_or_status = cipher->Encrypt(message, aad);
    EXPECT_TRUE(ct_or_status.ok());
    auto ct = ct_or_status.ValueOrDie();
    auto pt_or_status = cipher->Decrypt(ct, aad);
    EXPECT_TRUE(pt_or_status.ok()) << pt_or_status.status();
    auto pt = pt_or_status.ValueOrDie();
    EXPECT_EQ("", pt);
  }
  {  // Both are nullptr.
    auto ct_or_status = cipher->Encrypt(nullptr, nullptr);
    EXPECT_TRUE(ct_or_status.ok());
    auto ct = ct_or_status.ValueOrDie();
    auto pt_or_status = cipher->Decrypt(ct, nullptr);
    EXPECT_TRUE(pt_or_status.ok()) << pt_or_status.status();
    auto pt = pt_or_status.ValueOrDie();
    EXPECT_EQ("", pt);
  }
}

TEST(XChacha20Poly1305BoringSslTest, TestInvalidKeySizes) {
  if (kUseOnlyFips) {
    GTEST_SKIP() << "Not supported in FIPS-only mode";
  }

  for (int keysize = 0; keysize < 65; keysize++) {
    if (keysize == 32) {
      continue;
    }
    util::SecretData key(keysize, 'x');
    auto cipher = XChacha20Poly1305BoringSsl::New(key);
    EXPECT_FALSE(cipher.ok());
  }
}

TEST(XChacha20Poly1305BoringSslTest, TestFipsOnly) {
  if (!kUseOnlyFips) {
    GTEST_SKIP() << "Only supported in FIPS-only mode";
  }

  util::SecretData key256 = util::SecretDataFromStringView(test::HexDecodeOrDie(
      "000102030405060708090a0b0c0d0e0f000102030405060708090a0b0c0d0e0f"));

  auto xchacha20_poly1305_res = subtle::XChacha20Poly1305BoringSsl::New(key256);
  EXPECT_THAT(xchacha20_poly1305_res.status(), StatusIs(util::error::INTERNAL));
}

}  // namespace
}  // namespace subtle
}  // namespace tink
}  // namespace crypto
