/* Copyright (c) 2020, Google Inc.
 *
 * Permission to use, copy, modify, and/or distribute this software for any
 * purpose with or without fee is hereby granted, provided that the above
 * copyright notice and this permission notice appear in all copies.
 *
 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY
 * SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION
 * OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN
 * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. */

#include <stdio.h>
#include <string.h>

#include <string>

#include <openssl/base.h>
#include <openssl/aead.h>
#include <openssl/crypto.h>
#include <openssl/cipher.h>
#include <openssl/mem.h>

#include <gtest/gtest.h>

#include "internal.h"


// Test that OPENSSL_VERSION_NUMBER and OPENSSL_VERSION_TEXT are consistent.
// Node.js parses the version out of OPENSSL_VERSION_TEXT instead of using
// OPENSSL_VERSION_NUMBER.
TEST(CryptoTest, Version) {
  char expected[512];
  snprintf(expected, sizeof(expected), "OpenSSL %d.%d.%d ",
           OPENSSL_VERSION_NUMBER >> 28, (OPENSSL_VERSION_NUMBER >> 20) & 0xff,
           (OPENSSL_VERSION_NUMBER >> 12) & 0xff);
  EXPECT_EQ(expected,
            std::string(OPENSSL_VERSION_TEXT).substr(0, strlen(expected)));
}

TEST(CryptoTest, Strndup) {
  bssl::UniquePtr<char> str(OPENSSL_strndup(nullptr, 0));
  EXPECT_TRUE(str);
  EXPECT_STREQ("", str.get());
}

TEST(CryptoTest, ByteSwap) {
  EXPECT_EQ(0x04030201u, CRYPTO_bswap4(0x01020304u));
  EXPECT_EQ(UINT64_C(0x0807060504030201),
            CRYPTO_bswap8(UINT64_C(0x0102030405060708)));
}

#if defined(BORINGSSL_FIPS_COUNTERS)
using CounterArray = size_t[fips_counter_max + 1];

static void read_all_counters(CounterArray counters) {
  for (int counter = 0; counter <= fips_counter_max; counter++) {
    counters[counter] = FIPS_read_counter(static_cast<fips_counter_t>(counter));
  }
}

static void expect_counter_delta_is_zero_except_for_a_one_at(
    CounterArray before, CounterArray after, fips_counter_t position) {
  for (int counter = 0; counter <= fips_counter_max; counter++) {
    const size_t expected_delta = counter == position ? 1 : 0;
    EXPECT_EQ(after[counter], before[counter] + expected_delta) << counter;
  }
}

TEST(CryptoTest, FIPSCountersEVP) {
  constexpr struct {
    const EVP_CIPHER *(*cipher)();
    fips_counter_t counter;
  } kTests[] = {
      {
          EVP_aes_128_gcm,
          fips_counter_evp_aes_128_gcm,
      },
      {
          EVP_aes_256_gcm,
          fips_counter_evp_aes_256_gcm,
      },
      {
          EVP_aes_128_ctr,
          fips_counter_evp_aes_128_ctr,
      },
      {
          EVP_aes_256_ctr,
          fips_counter_evp_aes_256_ctr,
      },
  };

  uint8_t key[EVP_MAX_KEY_LENGTH] = {0};
  uint8_t iv[EVP_MAX_IV_LENGTH] = {1};
  CounterArray before, after;
  for (const auto &test : kTests) {
    read_all_counters(before);
    bssl::ScopedEVP_CIPHER_CTX ctx;
    ASSERT_TRUE(EVP_EncryptInit_ex(ctx.get(), test.cipher(), /*engine=*/nullptr,
                                   key, iv));
    read_all_counters(after);

    expect_counter_delta_is_zero_except_for_a_one_at(before, after,
                                                     test.counter);
  }
}

TEST(CryptoTest, FIPSCountersEVP_AEAD) {
  constexpr struct {
    const EVP_AEAD *(*aead)();
    unsigned key_len;
    fips_counter_t counter;
  } kTests[] = {
      {
          EVP_aead_aes_128_gcm,
          16,
          fips_counter_evp_aes_128_gcm,
      },
      {
          EVP_aead_aes_256_gcm,
          32,
          fips_counter_evp_aes_256_gcm,
      },
  };

  uint8_t key[EVP_AEAD_MAX_KEY_LENGTH] = {0};
  CounterArray before, after;
  for (const auto &test : kTests) {
    ASSERT_LE(test.key_len, sizeof(key));

    read_all_counters(before);
    bssl::ScopedEVP_AEAD_CTX ctx;
    ASSERT_TRUE(EVP_AEAD_CTX_init(ctx.get(), test.aead(), key, test.key_len,
                                  EVP_AEAD_DEFAULT_TAG_LENGTH,
                                  /*engine=*/nullptr));
    read_all_counters(after);

    expect_counter_delta_is_zero_except_for_a_one_at(before, after,
                                                     test.counter);
  }
}

#endif  // BORINGSSL_FIPS_COUNTERS

TEST(Crypto, QueryAlgorithmStatus) {
#if defined(BORINGSSL_FIPS)
  const bool is_fips_build = true;
#else
  const bool is_fips_build = false;
#endif

  EXPECT_EQ(FIPS_query_algorithm_status("AES-GCM"), is_fips_build);
  EXPECT_EQ(FIPS_query_algorithm_status("AES-ECB"), is_fips_build);

  EXPECT_FALSE(FIPS_query_algorithm_status("FakeEncrypt"));
  EXPECT_FALSE(FIPS_query_algorithm_status(""));
}

#if defined(BORINGSSL_FIPS) && !defined(OPENSSL_ASAN)
TEST(Crypto, OnDemandIntegrityTest) {
  BORINGSSL_integrity_test();
}
#endif

OPENSSL_DEPRECATED static void DeprecatedFunction() {}

OPENSSL_BEGIN_ALLOW_DEPRECATED
TEST(CryptoTest, DeprecatedFunction) {
  // This is deprecated, but should not trigger any warnings.
  DeprecatedFunction();
}
OPENSSL_END_ALLOW_DEPRECATED
