// 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 "libhwsec-foundation/utility/crypto.h"

#include <limits>
#include <string>
#include <vector>

#include <base/logging.h>
#include <base/optional.h>
#include <brillo/secure_blob.h>
#include <crypto/scoped_openssl_types.h>
#include <openssl/bio.h>
#include <openssl/err.h>
#include <openssl/rand.h>
#include <openssl/x509.h>

namespace {

// The wrapper of OpenSSL i2d series function. It takes a OpenSSL i2d function
// and apply to |object|.
//
// The wrapper will always accept the non-const pointer of the object since
// unique_ptr::get will only return the non-const version. It will break the
// type deduction of template.
template <typename OpenSSLType>
base::Optional<std::vector<uint8_t>> OpenSSLObjectToBytes(
    int (*i2d_convert_function)(OpenSSLType*, unsigned char**),
    typename std::remove_const<OpenSSLType>::type* object) {
  if (object == nullptr) {
    return base::nullopt;
  }

  unsigned char* openssl_buffer = nullptr;

  int size = i2d_convert_function(object, &openssl_buffer);
  if (size < 0) {
    return base::nullopt;
  }

  crypto::ScopedOpenSSLBytes scoped_buffer(openssl_buffer);
  return std::vector<uint8_t>(openssl_buffer, openssl_buffer + size);
}

}  // namespace

namespace hwsec_foundation {
namespace utility {

brillo::SecureBlob CreateSecureRandomBlob(size_t length) {
  // OpenSSL takes a signed integer. Returns nullopt if the user requests
  // something too large.
  if (length > static_cast<size_t>(std::numeric_limits<int>::max())) {
    LOG(ERROR) << __func__ << ": length exceeds the limit of int.";
    return brillo::SecureBlob();
  }

  brillo::SecureBlob blob(length);
  if (!RAND_bytes(reinterpret_cast<unsigned char*>(blob.data()), length)) {
    LOG(ERROR) << __func__ << ": failed to generate " << length
               << " random bytes: " << GetOpensslError();
    return brillo::SecureBlob();
  }

  return blob;
}

std::string GetOpensslError() {
  BIO* bio = BIO_new(BIO_s_mem());
  ERR_print_errors(bio);
  char* data = nullptr;
  int data_len = BIO_get_mem_data(bio, &data);
  std::string error_string(data, data_len);
  BIO_free(bio);
  return error_string;
}

base::Optional<std::vector<uint8_t>> RsaKeyToSubjectPublicKeyInfoBytes(
    const crypto::ScopedRSA& key) {
  return OpenSSLObjectToBytes(i2d_RSA_PUBKEY, key.get());
}

base::Optional<std::vector<uint8_t>> EccKeyToSubjectPublicKeyInfoBytes(
    const crypto::ScopedEC_KEY& key) {
  return OpenSSLObjectToBytes(i2d_EC_PUBKEY, key.get());
}

}  // namespace utility
}  // namespace hwsec_foundation
