// Copyright 2019 The Chromium OS Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#include <utility>

#include <base/check.h>
#include <brillo/secure_blob.h>
#include <crypto/libcrypto-compat.h>
#include <crypto/scoped_openssl_types.h>
#include <gtest/gtest.h>
#include <openssl/bn.h>
#include <openssl/rsa.h>
#include <trousers/tss.h>
#include <trousers/trousers.h>  // NOLINT(build/include_alpha) - needs tss.h

#include "cryptohome/crypto/rsa.h"
#include "cryptohome/tpm1_static_utils.h"

using brillo::Blob;

namespace cryptohome {

namespace {

// Creates the blob of the TPM_PUBKEY structure that holds information about the
// given RSA public key.
Blob BuildRsaTpmPubkeyBlob(const RSA& rsa) {
  Blob modulus(RSA_size(&rsa));
  const BIGNUM* n;
  RSA_get0_key(&rsa, &n, nullptr, nullptr);
  EXPECT_EQ(BN_bn2bin(n, modulus.data()), modulus.size());

  // Build the TPM_RSA_KEY_PARMS structure.
  TPM_RSA_KEY_PARMS rsa_key_parms;
  rsa_key_parms.keyLength = RSA_size(&rsa) * 8;
  rsa_key_parms.numPrimes = 2;
  // The default exponent is assumed.
  rsa_key_parms.exponentSize = 0;
  rsa_key_parms.exponent = nullptr;

  // Convert the TPM_RSA_KEY_PARMS structure into blob.
  UINT64 offset = 0;
  Trspi_LoadBlob_RSA_KEY_PARMS(&offset, nullptr, &rsa_key_parms);
  Blob rsa_key_parms_blob(offset);
  offset = 0;
  Trspi_LoadBlob_RSA_KEY_PARMS(&offset, rsa_key_parms_blob.data(),
                               &rsa_key_parms);
  EXPECT_EQ(offset, rsa_key_parms_blob.size());

  // Build the TPM_PUBKEY structure.
  TPM_PUBKEY pubkey;
  pubkey.algorithmParms.algorithmID = TPM_ALG_RSA;
  pubkey.algorithmParms.encScheme = 0;
  pubkey.algorithmParms.sigScheme = 0;
  pubkey.algorithmParms.parmSize = rsa_key_parms_blob.size();
  pubkey.algorithmParms.parms = rsa_key_parms_blob.data();
  pubkey.pubKey.keyLength = modulus.size();
  pubkey.pubKey.key = const_cast<BYTE*>(modulus.data());

  // Convert the TPM_PUBKEY structure blob into blob.
  offset = 0;
  Trspi_LoadBlob_PUBKEY(&offset, nullptr, &pubkey);
  Blob pubkey_blob(offset);
  offset = 0;
  Trspi_LoadBlob_PUBKEY(&offset, pubkey_blob.data(), &pubkey);
  EXPECT_EQ(offset, pubkey_blob.size());
  return pubkey_blob;
}

class Tpm1StaticUtilsRsaKeyTest
    : public testing::TestWithParam<int /* rsa_key_size_bits */> {
 protected:
  void SetUp() {
    crypto::ScopedBIGNUM e(BN_new());
    CHECK(e);
    ASSERT_TRUE(BN_set_word(e.get(), kWellKnownExponent));
    rsa_.reset(RSA_new());
    CHECK(rsa_);
    ASSERT_TRUE(
        RSA_generate_key_ex(rsa_.get(), rsa_key_size_bits(), e.get(), nullptr));
  }

  int rsa_key_size_bits() const { return GetParam(); }

  RSA* rsa() { return rsa_.get(); }

 private:
  crypto::ScopedRSA rsa_;
};

}  // namespace

// Tests the ParseRsaFromTpmPubkeyBlob function with correct TPM_PUBKEY blobs.
TEST_P(Tpm1StaticUtilsRsaKeyTest, ParseRsaFromTpmPubkeyBlob) {
  const Blob pubkey_blob = BuildRsaTpmPubkeyBlob(*rsa());

  crypto::ScopedRSA parsed_rsa = ParseRsaFromTpmPubkeyBlob(pubkey_blob);
  ASSERT_TRUE(parsed_rsa);

  const BIGNUM* n;
  const BIGNUM* e;
  RSA_get0_key(rsa(), &n, &e, nullptr);

  const BIGNUM* parsed_n;
  const BIGNUM* parsed_e;
  RSA_get0_key(parsed_rsa.get(), &parsed_n, &parsed_e, nullptr);

  EXPECT_EQ(BN_cmp(n, parsed_n), 0);
  EXPECT_EQ(BN_cmp(e, parsed_e), 0);
}

INSTANTIATE_TEST_SUITE_P(,
                         Tpm1StaticUtilsRsaKeyTest,
                         testing::Values(512, 1024, 2048, 4096));

}  // namespace cryptohome
