// Copyright 2019 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/aes_gcm_hkdf_stream_segment_decrypter.h"

#include <string>
#include <vector>

#include "absl/strings/str_cat.h"
#include "tink/subtle/aes_gcm_hkdf_stream_segment_encrypter.h"
#include "tink/subtle/common_enums.h"
#include "tink/subtle/hkdf.h"
#include "tink/subtle/random.h"
#include "tink/subtle/stream_segment_encrypter.h"
#include "tink/util/status.h"
#include "tink/util/statusor.h"
#include "tink/util/test_util.h"
#include "gtest/gtest.h"


namespace crypto {
namespace tink {
namespace subtle {
namespace {

util::StatusOr<std::unique_ptr<StreamSegmentEncrypter>>
GetEncrypter(absl::string_view ikm,
             HashType hkdf_hash,
             int derived_key_size,
             int ciphertext_offset,
             int ciphertext_segment_size,
             absl::string_view associated_data) {
  AesGcmHkdfStreamSegmentEncrypter::Params params;
  params.salt = Random::GetRandomBytes(derived_key_size);
  auto hkdf_result = Hkdf::ComputeHkdf(
      hkdf_hash, ikm, params.salt, associated_data,
      derived_key_size);
  if (!hkdf_result.ok()) return hkdf_result.status();
  params.key_value = hkdf_result.ValueOrDie();
  params.ciphertext_offset = ciphertext_offset;
  params.ciphertext_segment_size = ciphertext_segment_size;
  return AesGcmHkdfStreamSegmentEncrypter::New(params);
}

TEST(AesGcmHkdfStreamSegmentDecrypterTest, testBasic) {
  for (int ikm_size : {16, 32}) {
    for (HashType hkdf_hash : {SHA1, SHA256, SHA512}) {
      for (int derived_key_size = 16;
           derived_key_size <= ikm_size;
           derived_key_size += 16) {
        for (int ciphertext_offset : {0, 5, 10}) {
          for (int ct_segment_size : {80, 128, 200}) {
            for (std::string associated_data : {"associated data", "42", ""}) {
              SCOPED_TRACE(absl::StrCat(
                  "hkdf_hash = ", EnumToString(hkdf_hash),
                  ", ikm_size = ", ikm_size,
                  ", associated_data = '", associated_data, "'",
                  ", derived_key_size = ", derived_key_size,
                  ", ciphertext_offset = ", ciphertext_offset,
                  ", ciphertext_segment_size = ", ct_segment_size));

              // Construct a decrypter.
              AesGcmHkdfStreamSegmentDecrypter::Params params;
              params.ikm = Random::GetRandomBytes(ikm_size);
              params.hkdf_hash = hkdf_hash;
              params.derived_key_size = derived_key_size;
              params.ciphertext_offset = ciphertext_offset;
              params.ciphertext_segment_size = ct_segment_size;
              params.associated_data = associated_data;
              auto result = AesGcmHkdfStreamSegmentDecrypter::New(params);
              EXPECT_TRUE(result.ok()) << result.status();
              auto dec = std::move(result.ValueOrDie());

              // Try to use the decrypter.
              std::vector<uint8_t> pt;
              auto status = dec->DecryptSegment(pt, 42, false, nullptr);
              EXPECT_FALSE(status.ok());
              EXPECT_EQ(util::error::FAILED_PRECONDITION, status.error_code());
              EXPECT_PRED_FORMAT2(testing::IsSubstring, "not initialized",
                                  status.error_message());

              // Get an encrypter and initialize the decrypter.
              auto enc = std::move(
                  GetEncrypter(params.ikm, hkdf_hash, derived_key_size,
                               ciphertext_offset, ct_segment_size,
                               associated_data).ValueOrDie());
              status = dec->Init(enc->get_header());
              EXPECT_TRUE(status.ok()) << status;

              // Use the constructed decrypter.
              int header_size =
                  derived_key_size + /* nonce_prefix_size = */ 7 + 1;
              EXPECT_EQ(header_size, dec->get_header_size());
              EXPECT_EQ(enc->get_header().size(), dec->get_header_size());
              EXPECT_EQ(ct_segment_size, dec->get_ciphertext_segment_size());
              EXPECT_EQ(ct_segment_size - /* tag_size = */ 16,
                        dec->get_plaintext_segment_size());
              EXPECT_EQ(ciphertext_offset, dec->get_ciphertext_offset());
              int segment_number = 0;
              for (int pt_size : {1, 10, dec->get_plaintext_segment_size()}) {
                for (bool is_last_segment : {false, true}) {
                  SCOPED_TRACE(absl::StrCat(
                      "plaintext_size = ", pt_size,
                      ", is_last_segment = ", is_last_segment));
                  std::vector<uint8_t> pt(pt_size, 'p');
                  std::vector<uint8_t> ct;
                  std::vector<uint8_t> decrypted;
                  auto status = enc->EncryptSegment(pt, is_last_segment, &ct);
                  EXPECT_TRUE(status.ok()) << status;
                  status = dec->DecryptSegment(ct, segment_number,
                                               is_last_segment, &decrypted);
                  EXPECT_TRUE(status.ok()) << status;
                  EXPECT_EQ(pt, decrypted);
                  segment_number++;
                  EXPECT_EQ(segment_number, enc->get_segment_number());
                }
              }

              // Try decryption with wrong params.
              std::vector<uint8_t> ct(
                  dec->get_ciphertext_segment_size() + 1, 'c');
              status = dec->DecryptSegment(ct, 42, true, nullptr);
              EXPECT_FALSE(status.ok());
              EXPECT_PRED_FORMAT2(testing::IsSubstring, "ciphertext too long",
                                  status.error_message());
              ct.resize(dec->get_plaintext_segment_size());
              status = dec->DecryptSegment(ct, 42, true, nullptr);
              EXPECT_FALSE(status.ok());
              EXPECT_PRED_FORMAT2(testing::IsSubstring, "must be non-null",
                                  status.error_message());
            }
          }
        }
      }
    }
  }
}


TEST(AesGcmHkdfStreamSegmentDecrypterTest, testWrongDerivedKeySize) {
  for (int derived_key_size : {12, 24, 64}) {
    for (HashType hkdf_hash : {SHA1, SHA256, SHA512}) {
      for (int ct_segment_size : {128, 200}) {
        SCOPED_TRACE(absl::StrCat(
            "derived_key_size = ", derived_key_size,
            ", hkdf_hash = ", EnumToString(hkdf_hash),
            ", ciphertext_segment_size = ", ct_segment_size));
        AesGcmHkdfStreamSegmentDecrypter::Params params;
        params.ikm = Random::GetRandomBytes(derived_key_size);
        params.hkdf_hash = hkdf_hash;
        params.derived_key_size = derived_key_size;
        params.ciphertext_offset = 0;
        params.ciphertext_segment_size = ct_segment_size;
        params.associated_data = "associated data";
        auto result = AesGcmHkdfStreamSegmentDecrypter::New(params);
        EXPECT_FALSE(result.ok());
        EXPECT_EQ(util::error::INVALID_ARGUMENT, result.status().error_code());
        EXPECT_PRED_FORMAT2(testing::IsSubstring, "must be 16 or 32",
                            result.status().error_message());
      }
    }
  }
}

TEST(AesGcmHkdfStreamSegmentDecrypterTest, testWrongIkmSize) {
  for (int derived_key_size : {16, 32}) {
    for (HashType hkdf_hash : {SHA1, SHA256, SHA512}) {
      for (int ikm_size_delta : {-8, -4, -2, -1}) {
        SCOPED_TRACE(absl::StrCat(
            "derived_key_size = ", derived_key_size,
            ", hkdf_hash = ", EnumToString(hkdf_hash),
            ", ikm_size_delta = ", ikm_size_delta));
        AesGcmHkdfStreamSegmentDecrypter::Params params;
        params.ikm = Random::GetRandomBytes(derived_key_size + ikm_size_delta);
        params.hkdf_hash = hkdf_hash;
        params.derived_key_size = derived_key_size;
        params.ciphertext_offset = 0;
        params.ciphertext_segment_size = 128;
        params.associated_data = "associated data";
        auto result = AesGcmHkdfStreamSegmentDecrypter::New(params);
        EXPECT_FALSE(result.ok());
        EXPECT_EQ(util::error::INVALID_ARGUMENT, result.status().error_code());
        EXPECT_PRED_FORMAT2(testing::IsSubstring, "ikm too small",
                            result.status().error_message());
      }
    }
  }
}

TEST(AesGcmHkdfStreamSegmentDecrypterTest, testWrongCiphertextOffset) {
  for (int derived_key_size : {16, 32}) {
    for (HashType hkdf_hash : {SHA1, SHA256, SHA512}) {
      for (int ciphertext_offset : {-16, -10, -3, -1}) {
        SCOPED_TRACE(absl::StrCat(
            "derived_key_size = ", derived_key_size,
            ", hkdf_hash = ", EnumToString(hkdf_hash),
            ", ciphertext_offset = ", ciphertext_offset));
        AesGcmHkdfStreamSegmentDecrypter::Params params;
        params.ikm = Random::GetRandomBytes(derived_key_size);
        params.hkdf_hash = hkdf_hash;
        params.derived_key_size = derived_key_size;
        params.ciphertext_offset = ciphertext_offset;
        params.ciphertext_segment_size = 128;
        params.associated_data = "associated data";
        auto result = AesGcmHkdfStreamSegmentDecrypter::New(params);
        EXPECT_FALSE(result.ok());
        EXPECT_EQ(util::error::INVALID_ARGUMENT, result.status().error_code());
        EXPECT_PRED_FORMAT2(testing::IsSubstring, "must be non-negative",
                            result.status().error_message());
      }
    }
  }
}

TEST(AesGcmHkdfStreamSegmentDecrypterTest, testWrongCiphertextSegmentSize) {
  for (int derived_key_size : {16, 32}) {
    for (HashType hkdf_hash : {SHA1, SHA256, SHA512}) {
      for (int ciphertext_offset : {0, 1, 5, 10}) {
        int min_ct_segment_size = derived_key_size + ciphertext_offset +
                                  8 +   // nonce_prefix_size + 1
                                  16 +   // tag_size
                                  1;

        for (int ct_segment_size : {min_ct_segment_size - 5,
                min_ct_segment_size - 1, min_ct_segment_size,
                min_ct_segment_size + 1, min_ct_segment_size + 10}) {
          SCOPED_TRACE(absl::StrCat(
              "derived_key_size = ", derived_key_size,
              ", ciphertext_offset = ", ciphertext_offset,
              ", ciphertext_segment_size = ", ct_segment_size));
          AesGcmHkdfStreamSegmentDecrypter::Params params;
          params.ikm = Random::GetRandomBytes(derived_key_size);
          params.hkdf_hash = hkdf_hash;
          params.derived_key_size = derived_key_size;
          params.ciphertext_offset = ciphertext_offset;
          params.ciphertext_segment_size = ct_segment_size;
          auto result = AesGcmHkdfStreamSegmentDecrypter::New(params);
          if (ct_segment_size < min_ct_segment_size) {
            EXPECT_FALSE(result.ok());
            EXPECT_EQ(util::error::INVALID_ARGUMENT,
                      result.status().error_code());
            EXPECT_PRED_FORMAT2(testing::IsSubstring, "too small",
                                result.status().error_message());
          } else {
            EXPECT_TRUE(result.ok()) << result.status();
          }
        }
      }
    }
  }
}

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