| // 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. | |
| // | |
| #ifndef THIRD_PARTY_CREDENTIO_CRYPTO_CRYPTO_READ_HANDLER_H_ | |
| #define THIRD_PARTY_CREDENTIO_CRYPTO_CRYPTO_READ_HANDLER_H_ | |
| #include <cstddef> | |
| #include <memory> | |
| #include <string> | |
| #include <vector> | |
| #include "absl/status/status.h" | |
| #include "absl/status/statusor.h" | |
| #include "absl/strings/string_view.h" | |
| #include "absl/time/time.h" | |
| #include "absl/types/span.h" | |
| #include "crypto/algorithms.h" | |
| #include "crypto/timestamp_read_handler.h" | |
| namespace credentio { | |
| // A parsed public-key certificate with optional supporting intermediate certs. | |
| class ParsedCertificates { | |
| public: | |
| virtual ~ParsedCertificates() = default; | |
| // Verifies a raw signature extracted from a COSE_Sign1 message using the | |
| // public key from the leaf certificate. This is for use with COSE signatures | |
| // only, so ECDSA signatures must be in IEEE P1363 (not DER) format. Returns | |
| // an OK status if the verification is successful. Performs no trust checks. | |
| // | |
| // Returns: | |
| // - INVALID_ARGUMENT if the signature is invalid. | |
| virtual absl::Status VerifyCoseSignature( | |
| absl::string_view signature, absl::string_view data, | |
| SigningAlgorithm algorithm) const = 0; | |
| // Verifies the trustworthiness of the leaf certificate for claim signing, by | |
| // finding an ordered chain of valid certificates to a trusted root, | |
| // making use of the provided intermediate certificates as needed. All | |
| // certificate checks are performed in accordance with | |
| // https://spec.c2pa.org/specifications/specifications/2.4/specs/C2PA_Specification.html#_general_requirements, | |
| // and validity period checks are performed based on the provided time. | |
| // | |
| // Returns: | |
| // - UNAUTHENTICATED if the certificate cannot be trusted. | |
| // - OUT_OF_RANGE if `content_time` is outside the validity period of a | |
| // certificate. | |
| // - INVALID_ARGUMENT if a certificate is invalid. | |
| // - UNAVAILABLE if the root trust list cannot be accessed (only possible on | |
| // platforms where it is not built into the binary). | |
| // - The verified trust chain from leaf to root (including the relevant | |
| // trust anchor's cert) if the verification is successful. | |
| virtual absl::StatusOr<std::vector<std::string>> VerifyClaimSignerTrust( | |
| absl::Time content_time) const = 0; | |
| // Returns the number of certificates in the chain. Index 0 is the leaf | |
| // certificate, but the order of the other certificates is not guaranteed | |
| // and not all of them are necessarily part of the chain to a trust anchor | |
| // that a successful call to VerifyClaimSignerTrust finds. There is always at | |
| // least 1 certificate. | |
| virtual size_t GetCertificateCount() const = 0; | |
| // Returns the distinguished name of the subject of the certificate | |
| // (RFC 2253 format). Index 0 represents the leaf certificate. | |
| virtual absl::StatusOr<std::string> GetSubject(size_t index) const = 0; | |
| // Returns the distinguished name of the issuer of the certificate | |
| // (RFC 2253 format). | |
| virtual absl::StatusOr<std::string> GetIssuer(size_t index) const = 0; | |
| // Returns the certificates's start time (notBefore). | |
| virtual absl::StatusOr<absl::Time> GetStartTime(size_t index) const = 0; | |
| // Returns the certificate's end time (notAfter) | |
| virtual absl::StatusOr<absl::Time> GetEndTime(size_t index) const = 0; | |
| // Returns the certificate's serial number as a lowercase hex string. | |
| virtual absl::StatusOr<std::string> GetSerialNumberHex( | |
| size_t index) const = 0; | |
| // Returns the certificate's C2PA assurance level as a string (e.g., | |
| // "1.3.6.1.4.1.62558.3.10"), if it is present and can be parsed. | |
| // This is only relevant for the leaf certificate (index 0). | |
| virtual absl::StatusOr<std::string> GetAssuranceLevel(size_t index) const = 0; | |
| // Returns the certificate's C2PA conforming product ID. | |
| // This is only relevant for the leaf certificate (index 0). | |
| virtual absl::StatusOr<std::string> GetConformingProductId( | |
| size_t index) const = 0; | |
| }; | |
| // Represents the certificate revocation status returned by the OCSP | |
| // responder, as defined in RFC 6960 (Section 2.2). | |
| enum class OCSPRevocationStatus { | |
| kUnknown, // The responder does not know the status of the certificate. | |
| kGood, // The certificate is not revoked (valid). | |
| kRevoked, // The certificate has been revoked. | |
| }; | |
| // Encapsulates the crypto operation involved in claim verification. | |
| class CryptoReadHandler : public TimestampReadHandler { | |
| public: | |
| enum class TrustEnvironment { | |
| kUnspecified, | |
| // Trust any certificates, i.e., skip claim signer and timestamp trust | |
| // checks. | |
| kAny, | |
| // Trust dev certificates only. | |
| kDevOnly, | |
| // Trust qual certificates for signers and prod certificates for timestamps. | |
| kQualOnly, | |
| // Trust qual and prod certificates. | |
| kQualAndProd, | |
| // Trust prod certificates only. | |
| kProd, | |
| }; | |
| ~CryptoReadHandler() override = default; | |
| // Parses a set of DER-encoded certificates, the first of which is the | |
| // leaf certificate. | |
| virtual absl::StatusOr<std::unique_ptr<ParsedCertificates>> | |
| ParseCertificatesDer( | |
| absl::Span<const absl::string_view> certificates) const = 0; | |
| // Verifies the signature and validity of the DER-encoded OCSP response | |
| // against the provided issuer certificate (`issuer_certificate_der`) or | |
| // an authorized responder, and returns the revocation status of the target | |
| // certificate (`certificate_der`) at the specified `asserted_time`. | |
| // | |
| // The verification process ensures that the OCSP response is correctly signed | |
| // by the issuer or a delegated responder, conforms to RFC 6960 and C2PA | |
| // requirements, matches the target certificate, and is valid for | |
| // `asserted_time` and the current time (specifically, the current time is not | |
| // earlier than `thisUpdate` and either `asserted_time < thisUpdate` or | |
| // `asserted_time` is within the `[thisUpdate, nextUpdate)` interval). | |
| // | |
| // Arguments: | |
| // ocsp_response_der: The DER-encoded OCSP response. | |
| // certificate_der: The DER-encoded X.509 certificate whose revocation | |
| // status is being checked. | |
| // issuer_certificate_der: The DER-encoded X.509 certificate of the issuer | |
| // that signed `certificate_der`. | |
| // asserted_time: The time at which the certificate's revocation status is | |
| // evaluated. This is the time from the trusted timestamp, if any, and | |
| // otherwise the current time. | |
| // | |
| // Returns: | |
| // - INVALID_ARGUMENT if `certificate_der`, `issuer_certificate_der`, or the | |
| // OCSP response is malformed or invalid. | |
| // - UNAUTHENTICATED if the OCSP response signature fails verification or | |
| // if no matching response is found for `certificate_der`. | |
| // - OUT_OF_RANGE if `asserted_time` or the current time is outside the | |
| // valid time window of the OCSP response (e.g., based on `thisUpdate` and | |
| // `nextUpdate`). | |
| // - The verified `OCSPRevocationStatus` (kGood, kRevoked, or kUnknown) if | |
| // verification is successful. | |
| virtual absl::StatusOr<OCSPRevocationStatus> VerifyOcspResponse( | |
| absl::string_view ocsp_response_der, absl::string_view certificate_der, | |
| absl::string_view issuer_certificate_der, | |
| absl::Time asserted_time) const = 0; | |
| // Returns the trust environment of this handler. | |
| virtual TrustEnvironment trust_environment() const = 0; | |
| }; | |
| bool AbslParseFlag(absl::string_view text, | |
| CryptoReadHandler::TrustEnvironment* trust, | |
| std::string* error); | |
| std::string AbslUnparseFlag(CryptoReadHandler::TrustEnvironment trust); | |
| } // namespace credentio | |
| #endif // THIRD_PARTY_CREDENTIO_CRYPTO_CRYPTO_READ_HANDLER_H_ |