Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 0eaefff1 authored by Dmitry Dementyev's avatar Dmitry Dementyev
Browse files

Use old verification date for TestOnly certificate in recoverablekeystore.

Bug: 313931157
Test: atest RecoverableKeyStoreEndtoEndTest
Ignore-AOSP-First: development happens in internal branch.
Change-Id: Ic5a3be680d60744bb11fb83a0c32acf9f02ed9ae
parent 31b1d040
Loading
Loading
Loading
Loading
+9 −5
Original line number Diff line number Diff line
@@ -82,6 +82,7 @@ import java.security.cert.CertificateException;
import java.security.cert.X509Certificate;
import java.security.spec.InvalidKeySpecException;
import java.util.Arrays;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Locale;
@@ -272,9 +273,10 @@ public class RecoverableKeyStoreManager {
        CertPath certPath;
        X509Certificate rootCert =
                mTestCertHelper.getRootCertificate(rootCertificateAlias);
        Date validationDate = mTestCertHelper.getValidationDate(rootCertificateAlias);
        try {
            Log.d(TAG, "Getting and validating a random endpoint certificate");
            certPath = certXml.getRandomEndpointCert(rootCert);
            certPath = certXml.getRandomEndpointCert(rootCert, validationDate);
        } catch (CertValidationException e) {
            Log.e(TAG, "Invalid endpoint cert", e);
            throw new ServiceSpecificException(ERROR_INVALID_CERTIFICATE, e.getMessage());
@@ -348,10 +350,11 @@ public class RecoverableKeyStoreManager {

        X509Certificate rootCert =
                mTestCertHelper.getRootCertificate(rootCertificateAlias);
        Date validationDate = mTestCertHelper.getValidationDate(rootCertificateAlias);
        try {
            sigXml.verifyFileSignature(rootCert, recoveryServiceCertFile);
            sigXml.verifyFileSignature(rootCert, recoveryServiceCertFile, validationDate);
        } catch (CertValidationException e) {
            Log.d(TAG, "The signature over the cert file is invalid."
            Log.e(TAG, "The signature over the cert file is invalid."
                    + " Cert: " + HexDump.toHexString(recoveryServiceCertFile)
                    + " Sig: " + HexDump.toHexString(recoveryServiceSigFile));
            throw new ServiceSpecificException(ERROR_INVALID_CERTIFICATE, e.getMessage());
@@ -601,8 +604,9 @@ public class RecoverableKeyStoreManager {
        }

        try {
            CertUtils.validateCertPath(
                    mTestCertHelper.getRootCertificate(rootCertificateAlias), certPath);
            Date validationDate = mTestCertHelper.getValidationDate(rootCertificateAlias);
            CertUtils.validateCertPath(mTestCertHelper.getRootCertificate(rootCertificateAlias),
                    certPath, validationDate);
        } catch (CertValidationException e) {
            Log.e(TAG, "Failed to validate the given cert path", e);
            throw new ServiceSpecificException(ERROR_INVALID_CERTIFICATE, e.getMessage());
+13 −0
Original line number Diff line number Diff line
@@ -29,6 +29,7 @@ import android.util.Pair;
import com.android.internal.widget.LockPatternUtils;

import java.security.cert.X509Certificate;
import java.util.Date;
import java.util.HashMap;
import java.util.Map;

@@ -67,6 +68,18 @@ public class TestOnlyInsecureCertificateHelper {
        return rootCertificate;
    }

    /**
     * Returns hardcoded validation date for e2e tests.
     */
    public @Nullable Date getValidationDate(String rootCertificateAlias) {
        if (isTestOnlyCertificateAlias(rootCertificateAlias)) {
            // Certificate used for e2e test is expired.
            return new Date(2019 - 1900, 1, 30);
        } else {
            return null; // Use current time
        }
    }

    public @NonNull String getDefaultCertificateAliasIfEmpty(
            @Nullable String rootCertificateAlias) {
        if (rootCertificateAlias == null || rootCertificateAlias.isEmpty()) {
+4 −3
Original line number Diff line number Diff line
@@ -305,12 +305,13 @@ public final class CertUtils {
     *
     * @param trustedRoot the trusted root certificate
     * @param certPath the certificate path to be validated
     * @param validationDate use null for current time
     * @throws CertValidationException if the given certificate path is invalid, e.g., is expired,
     *                                 or does not have a valid signature
     */
    public static void validateCertPath(X509Certificate trustedRoot, CertPath certPath)
            throws CertValidationException {
        validateCertPath(/*validationDate=*/ null, trustedRoot, certPath);
    public static void validateCertPath(X509Certificate trustedRoot, CertPath certPath,
                @Nullable Date validationDate) throws CertValidationException {
        validateCertPath(validationDate, trustedRoot, certPath);
    }

    /**
+4 −3
Original line number Diff line number Diff line
@@ -76,15 +76,16 @@ public final class CertXml {
     * and returns the certificate path including the chosen certificate if it is valid.
     *
     * @param trustedRoot the trusted root certificate
     * @param validationDate use null for current time
     * @return the certificate path including the chosen certificate if the certificate is valid
     * @throws CertValidationException if the chosen certificate cannot be validated based on the
     *                                 trusted root certificate
     */
    public CertPath getRandomEndpointCert(X509Certificate trustedRoot)
            throws CertValidationException {
    public CertPath getRandomEndpointCert(X509Certificate trustedRoot,
            @Nullable Date validationDate)throws CertValidationException {
        return getEndpointCert(
                new SecureRandom().nextInt(this.endpointCerts.size()),
                /*validationDate=*/ null,
                validationDate,
                trustedRoot);
    }

+4 −10
Original line number Diff line number Diff line
@@ -18,7 +18,7 @@ package com.android.server.locksettings.recoverablekeystore.certificate;

import android.annotation.Nullable;

import com.android.internal.annotations.VisibleForTesting;
import org.w3c.dom.Element;

import java.security.cert.X509Certificate;
import java.util.ArrayList;
@@ -26,8 +26,6 @@ import java.util.Collections;
import java.util.Date;
import java.util.List;

import org.w3c.dom.Element;

/**
 * Parses and holds the XML file containing the signature of the XML file containing the list of THM
 * public-key certificates.
@@ -58,17 +56,13 @@ public final class SigXml {
     *
     * @param trustedRoot     the trusted root certificate
     * @param signedFileBytes the original file content that has been signed
     * @param validationDate use null for current time
     *
     * @throws CertValidationException if the signature verification fails, or the signer's
     *                                 certificate contained in this XML file cannot be validated
     *                                 based on the trusted root certificate
     */
    public void verifyFileSignature(X509Certificate trustedRoot, byte[] signedFileBytes)
            throws CertValidationException {
        verifyFileSignature(trustedRoot, signedFileBytes, /*validationDate=*/ null);
    }

    @VisibleForTesting
    void verifyFileSignature(
    public void verifyFileSignature(
            X509Certificate trustedRoot, byte[] signedFileBytes, @Nullable Date validationDate)
            throws CertValidationException {
        CertUtils.validateCert(validationDate, trustedRoot, intermediateCerts, signerCert);