// Copyright 2026 Google LLC
//
// 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
//
//    https://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 "crypto/default/x509_certificate.h"

#include <cstdint>
#include <ctime>
#include <memory>
#include <string>
#include <utility>
#include <vector>

#include "absl/base/no_destructor.h"
#include "absl/status/status.h"
#include "absl/status/status_macros.h"
#include "absl/status/statusor.h"
#include "absl/strings/ascii.h"
#include "absl/strings/str_cat.h"
#include "absl/strings/string_view.h"
#include "absl/strings/substitute.h"
#include "absl/time/time.h"
#include "crypto/algorithms.h"
#include "crypto/default/compliance_checker.h"
#include "openssl/asn1.h"
#include "openssl/base.h"
#include "openssl/bio.h"
#include "openssl/bn.h"
#include "openssl/evp.h"
#include "openssl/obj.h"
#include "openssl/pem.h"
#include "openssl/pool.h"
#include "openssl/rsa.h"
#include "openssl/x509.h"
#include "proto/common.pb.h"
#include "tink/cleartext_keyset_handle.h"
#include "tink/public_key_verify.h"
#include "tink/signature/config_v0.h"
#include "tink/signature/signature_pem_keyset_reader.h"

namespace credentio {
namespace {

using ::crypto::tink::PemKeyParams;
using ::crypto::tink::SignaturePemKeysetReaderBuilder;

// c2pa-al from
// https://github.com/c2pa-org/conformance-public/blob/main/docs/current/schemas/mib/oid.txt
constexpr char kAssuranceLevelOid[] = "1.3.6.1.4.1.62558.3";
// c2pa-cpl-record from
// https://github.com/c2pa-org/conformance-public/blob/main/docs/current/schemas/mib/oid.txt
constexpr char kConformanceRecordOid[] = "1.3.6.1.4.1.62558.4";

absl::Status CheckCompatibleWithAlgorithm(EVP_PKEY* pub_key,
                                          SigningAlgorithm algorithm) {
  int key_type = EVP_PKEY_id(pub_key);
  switch (algorithm) {
    case SigningAlgorithm::kPs256:
    case SigningAlgorithm::kPs384:
    case SigningAlgorithm::kPs512:
      if (key_type == EVP_PKEY_RSA || key_type == EVP_PKEY_RSA_PSS) {
        return absl::OkStatus();
      }
      break;
    case SigningAlgorithm::kEs256:
    case SigningAlgorithm::kEs384:
    case SigningAlgorithm::kEs512:
      if (key_type == EVP_PKEY_EC) {
        return absl::OkStatus();
      }
      break;
    case SigningAlgorithm::kEdDsa:
      if (key_type == EVP_PKEY_ED25519) {
        return absl::OkStatus();
      }
      break;
  }
  return absl::InvalidArgumentError(absl::Substitute(
      "Wrong key type ($0) for algorithm $1", key_type, algorithm));
}

// Returns a list of C2PA supported algorithms.
// See
// https://spec.c2pa.org/specifications/specifications/2.4/specs/C2PA_Specification.html#certificate-requirements.
// Note: bssl::GetDefaultEVPAlgorithms() does not include RSA_PSS.
const std::vector<const EVP_PKEY_ALG*>& GetC2paEVPAlgorithms() {
  static const absl::NoDestructor<std::vector<const EVP_PKEY_ALG*>> kAlgorithms(
      {
          EVP_pkey_ec_p256(),
          EVP_pkey_ec_p384(),
          EVP_pkey_ec_p521(),
          EVP_pkey_rsa(),
          EVP_pkey_rsa_pss_sha256(),
          EVP_pkey_rsa_pss_sha384(),
          EVP_pkey_rsa_pss_sha512(),
          EVP_pkey_ed25519(),
      });
  return *kAlgorithms;
}

absl::StatusOr<bssl::UniquePtr<X509>> GetCertificateFromDER(
    absl::string_view der_data) {
  auto crypto_buffer = bssl::UniquePtr<CRYPTO_BUFFER>(
      CRYPTO_BUFFER_new(reinterpret_cast<const uint8_t*>(der_data.data()),
                        der_data.length(), /*pool=*/nullptr));
  const auto& algorithms = GetC2paEVPAlgorithms();
  bssl::UniquePtr<X509> cert(X509_parse_with_algorithms(
      crypto_buffer.get(), algorithms.data(), algorithms.size()));
  if (cert == nullptr) {
    return absl::InvalidArgumentError(
        "Failed to parse the X.509 certificate from DER bytes");
  }
  return cert;
}

absl::StatusOr<std::string> PemEncode(EVP_PKEY* pub_key) {
  bssl::UniquePtr<BIO> bio(BIO_new(BIO_s_mem()));
  if (PEM_write_bio_PUBKEY(bio.get(), pub_key) != 1) {
    return absl::InternalError("Failed to write pub key to BIO");
  }
  const uint8_t* pem;
  size_t pem_length = 0;
  if (BIO_mem_contents(bio.get(), &pem, &pem_length) != 1) {
    return absl::InternalError("Failed to get PEM string from BIO");
  }
  std::string pem_str(reinterpret_cast<const char*>(pem), pem_length);
  return pem_str;
}

bssl::UniquePtr<EVP_PKEY> MaybeConvertPssToRsa(
    bssl::UniquePtr<EVP_PKEY> pub_key) {
  // Tink uses BoringSSL to parse public keys from PEM, which does not support
  // id-RSASSA-PSS by default. Since Tink uses key templates, it doesn't care if
  // the original public key had the "restricted" RSA-PSS OID or the "standard"
  // RSA OID. It only cares about the modulus and exponent, then applies the PSS
  // logic defined in the GetPemKeyParams. Therefore, for compatibility, we turn
  // the "restricted" RSA-PSS public key to a "generic" RSA public key.
  RSA* rsa_params = EVP_PKEY_get1_RSA(pub_key.get());
  if (rsa_params != nullptr) {
    // Ideally, we should check if it is a RSA_PSS key. However, BoringSSL does
    // not implement RSA_get0_pss_params yet.
    bssl::UniquePtr<EVP_PKEY> rsa_key(EVP_PKEY_new());
    EVP_PKEY_assign_RSA(rsa_key.get(), rsa_params);
    return rsa_key;
  }
  return pub_key;
}

std::string X509NamePrintEx(const X509_NAME* name, uint64_t flags) {
  if (!name) return "";

  bssl::UniquePtr<BIO> bio(BIO_new(BIO_s_mem()));
  X509_NAME_print_ex(bio.get(), name, 0, flags);
  int size = BIO_pending(bio.get());
  std::string buffer(size, '\0');
  int bytes_read = BIO_read(bio.get(), buffer.data(), size);
  if (bytes_read != size) {
    return "";
  }
  return buffer;
}

}  // namespace

std::string X509Certificate::GetSubject() const {
  return X509NamePrintEx(X509_get_subject_name(cert_.get()), XN_FLAG_RFC2253);
}

std::string X509Certificate::GetIssuer() const {
  return X509NamePrintEx(X509_get_issuer_name(cert_.get()), XN_FLAG_RFC2253);
}

absl::StatusOr<std::unique_ptr<X509Certificate>> X509Certificate::Create(
    absl::string_view der) {
  ABSL_ASSIGN_OR_RETURN(auto x509, GetCertificateFromDER(der));
  return std::make_unique<X509Certificate>(std::move(x509));
}

absl::Status X509Certificate::IsValidC2paCertificate(bool is_leaf) const {
  return ComplianceChecker::IsValidC2paCertificate(cert_.get(), is_leaf);
}

absl::Status X509Certificate::VerifySignature(
    absl::string_view signature, absl::string_view data,
    SigningAlgorithm algorithm) const {
  bssl::UniquePtr<EVP_PKEY> pub_key(X509_get_pubkey(cert_.get()));
  if (pub_key == nullptr) {
    return absl::InvalidArgumentError(
        "Certificate does not have a valid public key");
  }
  pub_key = MaybeConvertPssToRsa(std::move(pub_key));
  ABSL_ASSIGN_OR_RETURN(auto pem_str, PemEncode(pub_key.get()));
  auto builder = SignaturePemKeysetReaderBuilder(
      SignaturePemKeysetReaderBuilder::PemReaderType::PUBLIC_KEY_VERIFY);
  auto params = GetPemKeyParams(algorithm);
  if (!params.ok()) {
    return absl::Status(params.status().code(),
                        absl::StrCat(params.status().message(),
                                     "; Failed to get PEM key params"));
  }
  for (const auto& param : *params) {
    builder.Add({.serialized_key = pem_str, .parameters = param});
  }
  auto reader = builder.Build();
  if (!reader.ok()) {
    return absl::Status(
        reader.status().code(),
        absl::StrCat(reader.status().message(),
                     "; Failed to construct the PEM KeysetReader"));
  }
  auto handle = crypto::tink::CleartextKeysetHandle::Read(*std::move(reader));
  if (!handle.ok()) {
    return absl::Status(handle.status().code(),
                        absl::StrCat(handle.status().message(),
                                     "; Failed to construct the KeysetHandle"));
  }
  auto verifier = (*handle)->GetPrimitive<crypto::tink::PublicKeyVerify>(
      crypto::tink::ConfigSignatureV0());
  if (!verifier.ok()) {
    return absl::Status(
        verifier.status().code(),
        absl::StrCat(verifier.status().message(),
                     "; Failed to construct the PublicKeyVerify primitive"));
  }
  auto status = (*verifier)->Verify(signature, data);
  if (!status.ok()) {
    return absl::InvalidArgumentError(absl::StrCat(
        "Tink verification failed with the status error: ", status.message()));
  }
  return absl::OkStatus();
}

std::string X509Certificate::DebugString() const {
  bssl::UniquePtr<BIO> bio(BIO_new(BIO_s_mem()));
  if (!X509_print(bio.get(), cert_.get())) {
    return "<X509_print failed>";
  }
  const uint8_t* data;
  size_t len;
  if (!BIO_mem_contents(bio.get(), &data, &len) || len == 0) {
    return "BIO_mem_contents failed";
  }
  return std::string(reinterpret_cast<const char*>(data), len);
}

absl::StatusOr<absl::Time> X509Certificate::StartTime() const {
  const ASN1_TIME* not_before = X509_get0_notBefore(cert_.get());
  if (not_before == nullptr) {
    return absl::InternalError("failed to get certificate start time");
  }
  int64_t posix_time;
  if (ASN1_TIME_to_posix(not_before, &posix_time) == 0) {
    return absl::InternalError("Invalid certificate start time");
  }
  return absl::FromUnixSeconds(posix_time);
}

absl::StatusOr<absl::Time> X509Certificate::EndTime() const {
  int64_t posix_time;
  const ASN1_TIME* not_after = X509_get0_notAfter(cert_.get());
  if (not_after == nullptr) {
    return absl::InternalError("failed to get certificate end time");
  }
  if (ASN1_TIME_to_posix(not_after, &posix_time) == 0) {
    return absl::InternalError("Invalid certificate end time");
  }
  return absl::FromUnixSeconds(posix_time);
}

absl::StatusOr<std::vector<PemKeyParams>> X509Certificate::GetPemKeyParams(
    SigningAlgorithm algorithm) const {
  bssl::UniquePtr<EVP_PKEY> pub_key(X509_get_pubkey(cert_.get()));
  if (pub_key == nullptr) {
    return absl::InvalidArgumentError(
        "Certificate does not have a valid public key");
  }
  ABSL_RETURN_IF_ERROR(CheckCompatibleWithAlgorithm(pub_key.get(), algorithm));
  size_t key_size = EVP_PKEY_bits(pub_key.get());
  switch (algorithm) {
    case SigningAlgorithm::kPs256:
      return std::vector<PemKeyParams>{PemKeyParams{
          .key_type = crypto::tink::PemKeyType::PEM_RSA,
          .algorithm = crypto::tink::PemAlgorithm::RSASSA_PSS,
          .key_size_in_bits = key_size,
          .hash_type = google::crypto::tink::HashType::SHA256,
      }};
    case SigningAlgorithm::kPs384:
      return std::vector<PemKeyParams>{PemKeyParams{
          .key_type = crypto::tink::PemKeyType::PEM_RSA,
          .algorithm = crypto::tink::PemAlgorithm::RSASSA_PSS,
          .key_size_in_bits = key_size,
          .hash_type = google::crypto::tink::HashType::SHA384,
      }};
    case SigningAlgorithm::kPs512:
      return std::vector<PemKeyParams>{PemKeyParams{
          .key_type = crypto::tink::PemKeyType::PEM_RSA,
          .algorithm = crypto::tink::PemAlgorithm::RSASSA_PSS,
          .key_size_in_bits = key_size,
          .hash_type = google::crypto::tink::HashType::SHA512,
      }};
    case SigningAlgorithm::kEs256:
      return std::vector<PemKeyParams>{
          PemKeyParams{
              .key_type = crypto::tink::PemKeyType::PEM_EC,
              .algorithm = crypto::tink::PemAlgorithm::ECDSA_IEEE,
              .key_size_in_bits = key_size,
              .hash_type = google::crypto::tink::HashType::SHA256,
          },
          PemKeyParams{
              .key_type = crypto::tink::PemKeyType::PEM_EC,
              .algorithm = crypto::tink::PemAlgorithm::ECDSA_DER,
              .key_size_in_bits = key_size,
              .hash_type = google::crypto::tink::HashType::SHA256,
          }};
    case SigningAlgorithm::kEs384:
      return std::vector<PemKeyParams>{
          PemKeyParams{
              .key_type = crypto::tink::PemKeyType::PEM_EC,
              .algorithm = crypto::tink::PemAlgorithm::ECDSA_IEEE,
              .key_size_in_bits = key_size,
              .hash_type = google::crypto::tink::HashType::SHA384,
          },
          PemKeyParams{
              .key_type = crypto::tink::PemKeyType::PEM_EC,
              .algorithm = crypto::tink::PemAlgorithm::ECDSA_DER,
              .key_size_in_bits = key_size,
              .hash_type = google::crypto::tink::HashType::SHA384,
          }};
    case SigningAlgorithm::kEs512:
      return std::vector<PemKeyParams>{
          PemKeyParams{
              .key_type = crypto::tink::PemKeyType::PEM_EC,
              .algorithm = crypto::tink::PemAlgorithm::ECDSA_IEEE,
              .key_size_in_bits = key_size,
              .hash_type = google::crypto::tink::HashType::SHA512,
          },
          PemKeyParams{
              .key_type = crypto::tink::PemKeyType::PEM_EC,
              .algorithm = crypto::tink::PemAlgorithm::ECDSA_DER,
              .key_size_in_bits = key_size,
              .hash_type = google::crypto::tink::HashType::SHA512,
          },
      };
    case SigningAlgorithm::kEdDsa:
      return std::vector<PemKeyParams>{PemKeyParams{
          .key_type = crypto::tink::PemKeyType::PEM_EC,
          .algorithm = crypto::tink::PemAlgorithm::ED25519,
          .key_size_in_bits = key_size,
          .hash_type = google::crypto::tink::HashType::SHA512,
      }};
  }
}

absl::StatusOr<std::string> X509Certificate::GetSerialNumberHex() const {
  const ASN1_INTEGER* serial = X509_get0_serialNumber(cert_.get());
  if (serial == nullptr) {
    return absl::InternalError("failed to get certificate serial number");
  }
  bssl::UniquePtr<BIGNUM> bn(ASN1_INTEGER_to_BN(serial, nullptr));
  if (!bn) {
    return absl::InternalError("failed to convert serial number to BIGNUM");
  }
  bssl::UniquePtr<char> hex(BN_bn2hex(bn.get()));
  if (!hex) {
    return absl::InternalError("failed to convert BIGNUM to hex");
  }
  return absl::AsciiStrToLower(hex.get());
}

absl::StatusOr<std::string> X509Certificate::GetAssuranceLevel() const {
  static const ASN1_OBJECT* const assurance_level_oid = []() {
    return OBJ_txt2obj(kAssuranceLevelOid, /*dont_search_names=*/1);
  }();
  if (assurance_level_oid == nullptr) {
    return absl::InternalError("Failed to parse assurance level OID");
  }

  int index = X509_get_ext_by_OBJ(cert_.get(), assurance_level_oid, -1);
  if (index == -1) {
    return absl::NotFoundError("assurance level extension not found");
  }

  const X509_EXTENSION* extension = X509_get_ext(cert_.get(), index);
  if (extension == nullptr) {
    return absl::NotFoundError("cannot extract assurance level extension");
  }

  const ASN1_OCTET_STRING* octet_str = X509_EXTENSION_get_data(extension);
  if (octet_str == nullptr) {
    return absl::NotFoundError("cannot extract assurance level extension data");
  }

  const unsigned char* p = ASN1_STRING_get0_data(octet_str);
  int64_t len = ASN1_STRING_length(octet_str);
  bssl::UniquePtr<ASN1_OBJECT> val_obj(d2i_ASN1_OBJECT(nullptr, &p, len));
  if (!val_obj) {
    return absl::NotFoundError("cannot parse assurance level value");
  }

  char buf[128];
  int res = OBJ_obj2txt(buf, sizeof(buf), val_obj.get(), /*no_name=*/1);
  if (res <= 0) {
    return absl::NotFoundError(
        "cannot convert assurance level value to string");
  }
  return std::string(buf);
}

absl::StatusOr<std::string> X509Certificate::GetConformingProductId() const {
  static const ASN1_OBJECT* const conformance_record_oid = []() {
    return OBJ_txt2obj(kConformanceRecordOid, /*dont_search_names=*/1);
  }();
  if (conformance_record_oid == nullptr) {
    return absl::InternalError("Failed to parse conformance record OID");
  }

  int index = X509_get_ext_by_OBJ(cert_.get(), conformance_record_oid, -1);
  if (index == -1) {
    return absl::NotFoundError("Conformance record extension not found");
  }

  const X509_EXTENSION* extension = X509_get_ext(cert_.get(), index);
  if (extension == nullptr) {
    return absl::NotFoundError(
        "Failed to retrieve conformance record extension");
  }

  const ASN1_OCTET_STRING* octet_str = X509_EXTENSION_get_data(extension);
  if (octet_str == nullptr) {
    return absl::NotFoundError("Conformance record extension data is null");
  }

  const unsigned char* p = ASN1_STRING_get0_data(octet_str);
  int64_t len = ASN1_STRING_length(octet_str);
  bssl::UniquePtr<ASN1_UTF8STRING> utf8_str(
      d2i_ASN1_UTF8STRING(nullptr, &p, len));
  if (!utf8_str) {
    return absl::NotFoundError("Failed to parse UUID as UTF8String");
  }

  return std::string(
      reinterpret_cast<const char*>(ASN1_STRING_get0_data(utf8_str.get())),
      ASN1_STRING_length(utf8_str.get()));
}

}  // namespace credentio
