<commit_before>/**
 * DSS - Digital Signature Services
 * Copyright (C) 2015 European Commission, provided under the CEF programme
 * 
 * This file is part of the "DSS - Digital Signature Services" project.
 * 
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 * 
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 * 
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
 */
package eu.europa.esig.dss.crl;

import static org.junit.jupiter.api.Assertions.assertArrayEquals;
import static org.junit.jupiter.api.Assertions.assertEquals;
import static org.junit.jupiter.api.Assertions.assertFalse;
import static org.junit.jupiter.api.Assertions.assertNotNull;
import static org.junit.jupiter.api.Assertions.assertNull;
import static org.junit.jupiter.api.Assertions.assertThrows;
import static org.junit.jupiter.api.Assertions.assertTrue;

import java.io.ByteArrayInputStream;
import java.io.InputStream;
import java.math.BigInteger;
import java.security.cert.CertificateException;
import java.security.cert.CertificateFactory;
import java.security.cert.X509CRLEntry;
import java.security.cert.X509Certificate;
import java.util.Base64;

import org.junit.jupiter.api.Test;

import eu.europa.esig.dss.enumerations.KeyUsageBit;
import eu.europa.esig.dss.enumerations.SignatureAlgorithm;
import eu.europa.esig.dss.model.DSSException;
import eu.europa.esig.dss.model.x509.CertificateToken;

public abstract class AbstractTestCRLUtils extends AbstractCRLParserTestUtils {

	private static final CertificateFactory certificateFactory;

	static {
		try {
			certificateFactory = CertificateFactory.getInstance("X.509");
		} catch (CertificateException e) {
			throw new DSSException("Platform does not support X509 certificate", e);
		}
	}

	@Test
	public void isValidCRL() throws Exception {
		try (InputStream is = AbstractTestCRLUtils.class.getResourceAsStream("/belgium2.crl");
				InputStream isCer = AbstractTestCRLUtils.class.getResourceAsStream("/belgiumrs2.crt")) {
			CertificateToken certificateToken = loadCert(isCer);
			CRLBinary crlBinary = CRLUtils.buildCRLBinary(toByteArray(is));
			CRLValidity validCRL = CRLUtils.buildCRLValidity(crlBinary, certificateToken);
			assertNotNull(validCRL);
			assertNotNull(validCRL.getIssuerToken());
			assertNotNull(validCRL.getSignatureAlgorithm());
			assertNotNull(validCRL.getThisUpdate());
			assertNotNull(validCRL.getNextUpdate());
			assertTrue(validCRL.isIssuerX509PrincipalMatches());
			assertTrue(validCRL.isSignatureIntact());
			assertTrue(validCRL.isValid());
			assertTrue(validCRL.isCrlSignKeyUsage());
			assertFalse(validCRL.isUnknownCriticalExtension());
			assertEquals(certificateToken, validCRL.getIssuerToken());
			assertNull(validCRL.getSignatureInvalidityReason());
			assertNull(validCRL.getUrl());
		}
	}

	@Test
	public void testUA() throws Exception {
		try (InputStream is = AbstractTestCRLUtils.class.getResourceAsStream("/CA-5358AA45-Full.crl");
				InputStream isCer = AbstractTestCRLUtils.class.getResourceAsStream("/CA-Justice-ECDSA-261217.cer")) {
			CertificateToken certificateToken = loadCert(isCer);
			CRLBinary crlBinary = CRLUtils.buildCRLBinary(toByteArray(is));
			CRLValidity validCRL = CRLUtils.buildCRLValidity(crlBinary, certificateToken);
			assertNotNull(validCRL);
			assertNotNull(validCRL.getIssuerToken());
			assertEquals(SignatureAlgorithm.ECDSA_SHA256, validCRL.getSignatureAlgorithm());
			assertNotNull(validCRL.getThisUpdate());
			assertNotNull(validCRL.getNextUpdate());
			assertTrue(validCRL.isIssuerX509PrincipalMatches());
			assertTrue(validCRL.isSignatureIntact());
			assertTrue(validCRL.isValid());
			assertTrue(validCRL.isCrlSignKeyUsage());
			assertFalse(validCRL.isUnknownCriticalExtension());
			assertEquals(certificateToken, validCRL.getIssuerToken());
			assertNull(validCRL.getSignatureInvalidityReason());
			assertNull(validCRL.getUrl());
		}
	}

	@Test
	public void isValidPEMCRL() throws Exception {
		try (InputStream is = AbstractTestCRLUtils.class.getResourceAsStream("/belgium2.pem.crl");
				InputStream isCer = AbstractTestCRLUtils.class.getResourceAsStream("/belgiumrs2.crt")) {
			CertificateToken certificateToken = loadCert(isCer);
			CRLBinary crlBinary = CRLUtils.buildCRLBinary(toByteArray(is));
			CRLValidity validCRL = CRLUtils.buildCRLValidity(crlBinary, certificateToken);
			assertNotNull(validCRL);
			assertNotNull(validCRL.getSignatureAlgorithm());
			assertNotNull(validCRL.getThisUpdate());
			assertNotNull(validCRL.getNextUpdate());
			assertTrue(validCRL.isIssuerX509PrincipalMatches());
			assertTrue(validCRL.isSignatureIntact());
			assertNotNull(validCRL.getIssuerToken());
			assertTrue(validCRL.isValid());
			assertTrue(validCRL.isCrlSignKeyUsage());
			assertFalse(validCRL.isUnknownCriticalExtension());
			assertEquals(certificateToken, validCRL.getIssuerToken());
			assertNull(validCRL.getSignatureInvalidityReason());
			assertNull(validCRL.getUrl());
		}
	}

	@Test
	public void isValidCRLWrongCertificate() throws Exception {
		try (InputStream is = AbstractTestCRLUtils.class.getResourceAsStream("/belgium2.crl");
				InputStream isCer = AbstractTestCRLUtils.class.getResourceAsStream("/citizen_ca.cer")) {
			CertificateToken certificateToken = loadCert(isCer);
			CRLBinary crlBinary = CRLUtils.buildCRLBinary(toByteArray(is));
			CRLValidity validCRL = CRLUtils.buildCRLValidity(crlBinary, certificateToken);
			assertNotNull(validCRL);
			assertNull(validCRL.getIssuerToken());
			assertNotNull(validCRL.getSignatureAlgorithm());
			assertNotNull(validCRL.getThisUpdate());
			assertNotNull(validCRL.getNextUpdate());
			assertFalse(validCRL.isIssuerX509PrincipalMatches());
			assertFalse(validCRL.isSignatureIntact());
			assertFalse(validCRL.isValid());
			assertNotNull(validCRL.getSignatureInvalidityReason());
		}
	}

	@Test
	public void testLTGRCA() throws Exception {
		try (InputStream is = AbstractTestCRLUtils.class.getResourceAsStream("/LTGRCA.crl");
				InputStream isCer = AbstractTestCRLUtils.class.getResourceAsStream("/citizen_ca.cer")) {

			CertificateToken certificateToken = loadCert(isCer);
			CRLBinary crlBinary = CRLUtils.buildCRLBinary(toByteArray(is));
			CRLValidity validCRL = CRLUtils.buildCRLValidity(crlBinary, certificateToken);

			assertEquals(SignatureAlgorithm.RSA_SHA1, validCRL.getSignatureAlgorithm());
			assertNotNull(validCRL.getThisUpdate());
			assertNotNull(validCRL.getNextUpdate());
			assertNull(validCRL.getExpiredCertsOnCRL());

			assertFalse(validCRL.isIssuerX509PrincipalMatches());
			assertFalse(validCRL.isSignatureIntact());
			assertFalse(validCRL.isValid());
		}
	}

	@Test
	public void testGetExpiredCertsOnCRL() throws Exception {
		try (InputStream is = AbstractTestCRLUtils.class.getResourceAsStream("/crl_with_expiredCertsOnCRL_extension.crl");
				InputStream isCer = AbstractTestCRLUtils.class.getResourceAsStream("/citizen_ca.cer")) {

			CertificateToken certificateToken = loadCert(isCer);
			CRLBinary crlBinary = CRLUtils.buildCRLBinary(toByteArray(is));
			CRLValidity validCRL = CRLUtils.buildCRLValidity(crlBinary, certificateToken);

			assertEquals(SignatureAlgorithm.RSA_SHA256, validCRL.getSignatureAlgorithm());
			assertNotNull(validCRL.getThisUpdate());
			assertNotNull(validCRL.getNextUpdate());
			assertNotNull(validCRL.getExpiredCertsOnCRL());
			assertNotNull(validCRL.getUrl());

			assertFalse(validCRL.isIssuerX509PrincipalMatches());
			assertFalse(validCRL.isSignatureIntact());
			assertFalse(validCRL.isValid());
		}
	}

	@Test
	public void testGetExpiredCertsOnCRLUTCTime() throws Exception {
		try (InputStream is = AbstractTestCRLUtils.class.getResourceAsStream("/crl-expiredCertsOnCRL-UTCTime.crl");
				InputStream isCer = AbstractTestCRLUtils.class.getResourceAsStream("/citizen_ca.cer")) {

			CertificateToken certificateToken = loadCert(isCer);
			CRLBinary crlBinary = CRLUtils.buildCRLBinary(toByteArray(is));
			CRLValidity validCRL = CRLUtils.buildCRLValidity(crlBinary, certificateToken);

			assertEquals(SignatureAlgorithm.RSA_SHA256, validCRL.getSignatureAlgorithm());
			assertNotNull(validCRL.getThisUpdate());
			assertNotNull(validCRL.getNextUpdate());
			assertNull(validCRL.getExpiredCertsOnCRL()); // Ignored
			assertNull(validCRL.getUrl());

			assertFalse(validCRL.isIssuerX509PrincipalMatches());
			assertFalse(validCRL.isSignatureIntact());
			assertFalse(validCRL.isValid());
		}
	}
	
	@Test
	public void derVsPemEncodedTest() throws Exception {
		try (InputStream isDer = AbstractTestCRLUtils.class.getResourceAsStream("/DSS-2039/crl.der");
				InputStream isPem = AbstractTestCRLUtils.class.getResourceAsStream("/DSS-2039/crl.pem");
				InputStream isCert = AbstractTestCRLUtils.class.getResourceAsStream("/DSS-2039/cert.pem");
				InputStream isCA = AbstractTestCRLUtils.class.getResourceAsStream("/DSS-2039/ca.pem") ) {

			CertificateToken cert = loadCert(isCert);
			CertificateToken ca = loadCert(isCA);
			
			CRLBinary crlBinaryDER = CRLUtils.buildCRLBinary(toByteArray(isDer));
			CRLValidity crlDER = CRLUtils.buildCRLValidity(crlBinaryDER, ca);
			
			CRLBinary crlBinaryPEM = CRLUtils.buildCRLBinary(toByteArray(isPem));
			CRLValidity crlPEM = CRLUtils.buildCRLValidity(crlBinaryPEM, ca);
			
			assertArrayEquals(crlDER.getDerEncoded(), crlPEM.getDerEncoded());
			
			X509CRLEntry revocationInfoDER = CRLUtils.getRevocationInfo(crlDER, cert.getSerialNumber());
			X509CRLEntry revocationInfoPEM = CRLUtils.getRevocationInfo(crlPEM, cert.getSerialNumber());
			assertEquals(revocationInfoDER, revocationInfoPEM);
		}
	}

	@Test
	public void retrieveRevocation() throws Exception {
		try (InputStream is = AbstractTestCRLUtils.class.getResourceAsStream("/http___crl.globalsign.com_gs_gspersonalsign2sha2g2.crl");
				InputStream isCer = AbstractTestCRLUtils.class.getResourceAsStream("/citizen_ca.cer")) {

			CertificateToken certificateToken = loadCert(isCer);

			CRLBinary crlBinary = CRLUtils.buildCRLBinary(toByteArray(is));
			CRLValidity validity = CRLUtils.buildCRLValidity(crlBinary, certificateToken);

			BigInteger serialNumber = new BigInteger("288350169419475868349393253038503091234");
			X509CRLEntry entry = CRLUtils.getRevocationInfo(validity, serialNumber);
			assertNotNull(entry);
			assertNotNull(entry.getRevocationDate());
			assertNull(entry.getRevocationReason());
			assertNotNull(entry.getSerialNumber());
			assertEquals(serialNumber, entry.getSerialNumber());

			serialNumber = new BigInteger("288350169419475868349393264025423631520");
			entry = CRLUtils.getRevocationInfo(validity, serialNumber);
			assertNotNull(entry);
			assertNotNull(entry.getRevocationDate());
			assertNull(entry.getRevocationReason());
			assertNotNull(entry.getSerialNumber());
			assertEquals(serialNumber, entry.getSerialNumber());

			serialNumber = new BigInteger("111111111111111111111111111");
			entry = CRLUtils.getRevocationInfo(validity, serialNumber);
			assertNull(entry);
		}
	}

	@Test
	public void testARLFile() throws Exception {
		try (InputStream is = AbstractTestCRLUtils.class.getResourceAsStream("/notaires2020.arl");
				InputStream isCer = AbstractTestCRLUtils.class.getResourceAsStream("/citizen_ca.cer")) {

			CertificateToken certificateToken = loadCert(isCer);

			CRLBinary crlBinary = CRLUtils.buildCRLBinary(toByteArray(is));
			CRLValidity validity = CRLUtils.buildCRLValidity(crlBinary, certificateToken);
			assertNotNull(validity);
			assertNotNull(validity.getThisUpdate());
			assertNotNull(validity.getNextUpdate());
			assertNotNull(validity.getSignatureAlgorithm());
		}
	}

	// @Ignore
	@Test
	public void testHugeCRL() throws Exception {
		try (InputStream is = AbstractTestCRLUtils.class.getResourceAsStream("/esteid2011.crl");
				InputStream isCer = AbstractTestCRLUtils.class.getResourceAsStream("/ESTEID-SK_2011.der.crt")) {

			CertificateToken certificateToken = loadCert(isCer);

			CRLBinary crlBinary = CRLUtils.buildCRLBinary(toByteArray(is));
			CRLValidity validity = CRLUtils.buildCRLValidity(crlBinary, certificateToken);

			assertEquals(SignatureAlgorithm.RSA_SHA256, validity.getSignatureAlgorithm());
			assertNotNull(validity.getThisUpdate());
			assertNotNull(validity.getNextUpdate());
			assertNull(validity.getExpiredCertsOnCRL());
			assertNotNull(validity.getIssuerToken());
			assertTrue(validity.isValid());

			BigInteger serialNumber = new BigInteger("1111111111111111111");
			assertNull(CRLUtils.getRevocationInfo(validity, serialNumber));
		}
	}

	@Test
	public void testRealNot() throws Exception {
		try (InputStream is = AbstractTestCRLUtils.class.getResourceAsStream("/realts2019.crl");
				InputStream isCer = AbstractTestCRLUtils.class.getResourceAsStream("/realts2019.crt")) {
			CertificateToken certificateToken = loadCert(isCer);
			CRLBinary crlBinary = CRLUtils.buildCRLBinary(toByteArray(is));
			CRLValidity wrongIssuerCRL = CRLUtils.buildCRLValidity(crlBinary, certificateToken);

			assertNotNull(wrongIssuerCRL);
			assertNull(wrongIssuerCRL.getIssuerToken());
			assertNotNull(wrongIssuerCRL.getThisUpdate());
			assertNotNull(wrongIssuerCRL.getNextUpdate());
			assertTrue(wrongIssuerCRL.isIssuerX509PrincipalMatches());
			assertNotNull(wrongIssuerCRL.getSignatureInvalidityReason());
			assertFalse(wrongIssuerCRL.isValid());
			assertEquals(SignatureAlgorithm.RSA_SHA256, wrongIssuerCRL.getSignatureAlgorithm());
		}
	}

	@Test
	public void testECDSA() throws Exception {
		try (InputStream is = AbstractTestCRLUtils.class.getResourceAsStream("/EE-GovCA2018.crl");
				InputStream isCer = AbstractTestCRLUtils.class.getResourceAsStream("/EE-GovCA2018.pem.crt")) {

			CertificateToken certificateToken = loadCert(isCer);

			CRLBinary crlBinary = CRLUtils.buildCRLBinary(toByteArray(is));
			CRLValidity validity = CRLUtils.buildCRLValidity(crlBinary, certificateToken);

			assertEquals(SignatureAlgorithm.ECDSA_SHA512, validity.getSignatureAlgorithm());
			assertNotNull(validity.getThisUpdate());
			assertNotNull(validity.getNextUpdate());
			assertNull(validity.getExpiredCertsOnCRL());
			assertNotNull(validity.getIssuerToken());
			assertTrue(validity.isValid());
		}
	}

	@Test
	public void testECDSAwithRSACert() throws Exception {
		try (InputStream is = AbstractTestCRLUtils.class.getResourceAsStream("/EE-GovCA2018.crl");
				InputStream isCer = AbstractTestCRLUtils.class.getResourceAsStream("/citizen_ca.cer")) {

			CertificateToken certificateToken = loadCert(isCer);

			CRLBinary crlBinary = CRLUtils.buildCRLBinary(toByteArray(is));
			CRLValidity validity = CRLUtils.buildCRLValidity(crlBinary, certificateToken);

			assertEquals(SignatureAlgorithm.ECDSA_SHA512, validity.getSignatureAlgorithm());
			assertNotNull(validity.getThisUpdate());
			assertNotNull(validity.getNextUpdate());
			assertNull(validity.getExpiredCertsOnCRL());
			assertNull(validity.getIssuerToken());
			assertFalse(validity.isValid());
		}
	}

	@Test
	public void testPSSwithoutBouncyCastle() throws Exception {
		try (InputStream is = AbstractTestCRLUtils.class.getResourceAsStream("/d-trust_root_ca_1_2017.crl");
				InputStream isCer = AbstractTestCRLUtils.class.getResourceAsStream("/D-TRUST_Root_CA_1_2017.crt")) {
			Exception exception = assertThrows(IllegalArgumentException.class, () -> loadCert(isCer));
			assertEquals("Unable to initialize PSS", exception.getMessage());
		}
	}

	@Test
	public void incompleteCRL() throws Exception {
		try (InputStream is = new ByteArrayInputStream(new byte[] { 1, 2, 3 })) {<commit_msg>DSS-2468 : JDK 16 support<commit_after>/**
 * DSS - Digital Signature Services
 * Copyright (C) 2015 European Commission, provided under the CEF programme
 * 
 * This file is part of the "DSS - Digital Signature Services" project.
 * 
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 * 
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 * 
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
 */
package eu.europa.esig.dss.crl;

import eu.europa.esig.dss.enumerations.KeyUsageBit;
import eu.europa.esig.dss.enumerations.SignatureAlgorithm;
import eu.europa.esig.dss.model.DSSException;
import eu.europa.esig.dss.model.x509.CertificateToken;
import org.junit.jupiter.api.Test;
import org.junit.jupiter.api.condition.DisabledForJreRange;
import org.junit.jupiter.api.condition.JRE;

import java.io.ByteArrayInputStream;
import java.io.InputStream;
import java.math.BigInteger;
import java.security.cert.CertificateException;
import java.security.cert.CertificateFactory;
import java.security.cert.X509CRLEntry;
import java.security.cert.X509Certificate;
import java.util.Base64;

import static org.junit.jupiter.api.Assertions.assertArrayEquals;
import static org.junit.jupiter.api.Assertions.assertEquals;
import static org.junit.jupiter.api.Assertions.assertFalse;
import static org.junit.jupiter.api.Assertions.assertNotNull;
import static org.junit.jupiter.api.Assertions.assertNull;
import static org.junit.jupiter.api.Assertions.assertThrows;
import static org.junit.jupiter.api.Assertions.assertTrue;

public abstract class AbstractTestCRLUtils extends AbstractCRLParserTestUtils {

	private static final CertificateFactory certificateFactory;

	static {
		try {
			certificateFactory = CertificateFactory.getInstance("X.509");
		} catch (CertificateException e) {
			throw new DSSException("Platform does not support X509 certificate", e);
		}
	}

	@Test
	public void isValidCRL() throws Exception {
		try (InputStream is = AbstractTestCRLUtils.class.getResourceAsStream("/belgium2.crl");
				InputStream isCer = AbstractTestCRLUtils.class.getResourceAsStream("/belgiumrs2.crt")) {
			CertificateToken certificateToken = loadCert(isCer);
			CRLBinary crlBinary = CRLUtils.buildCRLBinary(toByteArray(is));
			CRLValidity validCRL = CRLUtils.buildCRLValidity(crlBinary, certificateToken);
			assertNotNull(validCRL);
			assertNotNull(validCRL.getIssuerToken());
			assertNotNull(validCRL.getSignatureAlgorithm());
			assertNotNull(validCRL.getThisUpdate());
			assertNotNull(validCRL.getNextUpdate());
			assertTrue(validCRL.isIssuerX509PrincipalMatches());
			assertTrue(validCRL.isSignatureIntact());
			assertTrue(validCRL.isValid());
			assertTrue(validCRL.isCrlSignKeyUsage());
			assertFalse(validCRL.isUnknownCriticalExtension());
			assertEquals(certificateToken, validCRL.getIssuerToken());
			assertNull(validCRL.getSignatureInvalidityReason());
			assertNull(validCRL.getUrl());
		}
	}

	@Test
	public void testUA() throws Exception {
		try (InputStream is = AbstractTestCRLUtils.class.getResourceAsStream("/CA-5358AA45-Full.crl");
				InputStream isCer = AbstractTestCRLUtils.class.getResourceAsStream("/CA-Justice-ECDSA-261217.cer")) {
			CertificateToken certificateToken = loadCert(isCer);
			CRLBinary crlBinary = CRLUtils.buildCRLBinary(toByteArray(is));
			CRLValidity validCRL = CRLUtils.buildCRLValidity(crlBinary, certificateToken);
			assertNotNull(validCRL);
			assertNotNull(validCRL.getIssuerToken());
			assertEquals(SignatureAlgorithm.ECDSA_SHA256, validCRL.getSignatureAlgorithm());
			assertNotNull(validCRL.getThisUpdate());
			assertNotNull(validCRL.getNextUpdate());
			assertTrue(validCRL.isIssuerX509PrincipalMatches());
			assertTrue(validCRL.isSignatureIntact());
			assertTrue(validCRL.isValid());
			assertTrue(validCRL.isCrlSignKeyUsage());
			assertFalse(validCRL.isUnknownCriticalExtension());
			assertEquals(certificateToken, validCRL.getIssuerToken());
			assertNull(validCRL.getSignatureInvalidityReason());
			assertNull(validCRL.getUrl());
		}
	}

	@Test
	public void isValidPEMCRL() throws Exception {
		try (InputStream is = AbstractTestCRLUtils.class.getResourceAsStream("/belgium2.pem.crl");
				InputStream isCer = AbstractTestCRLUtils.class.getResourceAsStream("/belgiumrs2.crt")) {
			CertificateToken certificateToken = loadCert(isCer);
			CRLBinary crlBinary = CRLUtils.buildCRLBinary(toByteArray(is));
			CRLValidity validCRL = CRLUtils.buildCRLValidity(crlBinary, certificateToken);
			assertNotNull(validCRL);
			assertNotNull(validCRL.getSignatureAlgorithm());
			assertNotNull(validCRL.getThisUpdate());
			assertNotNull(validCRL.getNextUpdate());
			assertTrue(validCRL.isIssuerX509PrincipalMatches());
			assertTrue(validCRL.isSignatureIntact());
			assertNotNull(validCRL.getIssuerToken());
			assertTrue(validCRL.isValid());
			assertTrue(validCRL.isCrlSignKeyUsage());
			assertFalse(validCRL.isUnknownCriticalExtension());
			assertEquals(certificateToken, validCRL.getIssuerToken());
			assertNull(validCRL.getSignatureInvalidityReason());
			assertNull(validCRL.getUrl());
		}
	}

	@Test
	public void isValidCRLWrongCertificate() throws Exception {
		try (InputStream is = AbstractTestCRLUtils.class.getResourceAsStream("/belgium2.crl");
				InputStream isCer = AbstractTestCRLUtils.class.getResourceAsStream("/citizen_ca.cer")) {
			CertificateToken certificateToken = loadCert(isCer);
			CRLBinary crlBinary = CRLUtils.buildCRLBinary(toByteArray(is));
			CRLValidity validCRL = CRLUtils.buildCRLValidity(crlBinary, certificateToken);
			assertNotNull(validCRL);
			assertNull(validCRL.getIssuerToken());
			assertNotNull(validCRL.getSignatureAlgorithm());
			assertNotNull(validCRL.getThisUpdate());
			assertNotNull(validCRL.getNextUpdate());
			assertFalse(validCRL.isIssuerX509PrincipalMatches());
			assertFalse(validCRL.isSignatureIntact());
			assertFalse(validCRL.isValid());
			assertNotNull(validCRL.getSignatureInvalidityReason());
		}
	}

	@Test
	public void testLTGRCA() throws Exception {
		try (InputStream is = AbstractTestCRLUtils.class.getResourceAsStream("/LTGRCA.crl");
				InputStream isCer = AbstractTestCRLUtils.class.getResourceAsStream("/citizen_ca.cer")) {

			CertificateToken certificateToken = loadCert(isCer);
			CRLBinary crlBinary = CRLUtils.buildCRLBinary(toByteArray(is));
			CRLValidity validCRL = CRLUtils.buildCRLValidity(crlBinary, certificateToken);

			assertEquals(SignatureAlgorithm.RSA_SHA1, validCRL.getSignatureAlgorithm());
			assertNotNull(validCRL.getThisUpdate());
			assertNotNull(validCRL.getNextUpdate());
			assertNull(validCRL.getExpiredCertsOnCRL());

			assertFalse(validCRL.isIssuerX509PrincipalMatches());
			assertFalse(validCRL.isSignatureIntact());
			assertFalse(validCRL.isValid());
		}
	}

	@Test
	public void testGetExpiredCertsOnCRL() throws Exception {
		try (InputStream is = AbstractTestCRLUtils.class.getResourceAsStream("/crl_with_expiredCertsOnCRL_extension.crl");
				InputStream isCer = AbstractTestCRLUtils.class.getResourceAsStream("/citizen_ca.cer")) {

			CertificateToken certificateToken = loadCert(isCer);
			CRLBinary crlBinary = CRLUtils.buildCRLBinary(toByteArray(is));
			CRLValidity validCRL = CRLUtils.buildCRLValidity(crlBinary, certificateToken);

			assertEquals(SignatureAlgorithm.RSA_SHA256, validCRL.getSignatureAlgorithm());
			assertNotNull(validCRL.getThisUpdate());
			assertNotNull(validCRL.getNextUpdate());
			assertNotNull(validCRL.getExpiredCertsOnCRL());
			assertNotNull(validCRL.getUrl());

			assertFalse(validCRL.isIssuerX509PrincipalMatches());
			assertFalse(validCRL.isSignatureIntact());
			assertFalse(validCRL.isValid());
		}
	}

	@Test
	public void testGetExpiredCertsOnCRLUTCTime() throws Exception {
		try (InputStream is = AbstractTestCRLUtils.class.getResourceAsStream("/crl-expiredCertsOnCRL-UTCTime.crl");
				InputStream isCer = AbstractTestCRLUtils.class.getResourceAsStream("/citizen_ca.cer")) {

			CertificateToken certificateToken = loadCert(isCer);
			CRLBinary crlBinary = CRLUtils.buildCRLBinary(toByteArray(is));
			CRLValidity validCRL = CRLUtils.buildCRLValidity(crlBinary, certificateToken);

			assertEquals(SignatureAlgorithm.RSA_SHA256, validCRL.getSignatureAlgorithm());
			assertNotNull(validCRL.getThisUpdate());
			assertNotNull(validCRL.getNextUpdate());
			assertNull(validCRL.getExpiredCertsOnCRL()); // Ignored
			assertNull(validCRL.getUrl());

			assertFalse(validCRL.isIssuerX509PrincipalMatches());
			assertFalse(validCRL.isSignatureIntact());
			assertFalse(validCRL.isValid());
		}
	}
	
	@Test
	public void derVsPemEncodedTest() throws Exception {
		try (InputStream isDer = AbstractTestCRLUtils.class.getResourceAsStream("/DSS-2039/crl.der");
				InputStream isPem = AbstractTestCRLUtils.class.getResourceAsStream("/DSS-2039/crl.pem");
				InputStream isCert = AbstractTestCRLUtils.class.getResourceAsStream("/DSS-2039/cert.pem");
				InputStream isCA = AbstractTestCRLUtils.class.getResourceAsStream("/DSS-2039/ca.pem") ) {

			CertificateToken cert = loadCert(isCert);
			CertificateToken ca = loadCert(isCA);
			
			CRLBinary crlBinaryDER = CRLUtils.buildCRLBinary(toByteArray(isDer));
			CRLValidity crlDER = CRLUtils.buildCRLValidity(crlBinaryDER, ca);
			
			CRLBinary crlBinaryPEM = CRLUtils.buildCRLBinary(toByteArray(isPem));
			CRLValidity crlPEM = CRLUtils.buildCRLValidity(crlBinaryPEM, ca);
			
			assertArrayEquals(crlDER.getDerEncoded(), crlPEM.getDerEncoded());
			
			X509CRLEntry revocationInfoDER = CRLUtils.getRevocationInfo(crlDER, cert.getSerialNumber());
			X509CRLEntry revocationInfoPEM = CRLUtils.getRevocationInfo(crlPEM, cert.getSerialNumber());
			assertEquals(revocationInfoDER, revocationInfoPEM);
		}
	}

	@Test
	public void retrieveRevocation() throws Exception {
		try (InputStream is = AbstractTestCRLUtils.class.getResourceAsStream("/http___crl.globalsign.com_gs_gspersonalsign2sha2g2.crl");
				InputStream isCer = AbstractTestCRLUtils.class.getResourceAsStream("/citizen_ca.cer")) {

			CertificateToken certificateToken = loadCert(isCer);

			CRLBinary crlBinary = CRLUtils.buildCRLBinary(toByteArray(is));
			CRLValidity validity = CRLUtils.buildCRLValidity(crlBinary, certificateToken);

			BigInteger serialNumber = new BigInteger("288350169419475868349393253038503091234");
			X509CRLEntry entry = CRLUtils.getRevocationInfo(validity, serialNumber);
			assertNotNull(entry);
			assertNotNull(entry.getRevocationDate());
			assertNull(entry.getRevocationReason());
			assertNotNull(entry.getSerialNumber());
			assertEquals(serialNumber, entry.getSerialNumber());

			serialNumber = new BigInteger("288350169419475868349393264025423631520");
			entry = CRLUtils.getRevocationInfo(validity, serialNumber);
			assertNotNull(entry);
			assertNotNull(entry.getRevocationDate());
			assertNull(entry.getRevocationReason());
			assertNotNull(entry.getSerialNumber());
			assertEquals(serialNumber, entry.getSerialNumber());

			serialNumber = new BigInteger("111111111111111111111111111");
			entry = CRLUtils.getRevocationInfo(validity, serialNumber);
			assertNull(entry);
		}
	}

	@Test
	public void testARLFile() throws Exception {
		try (InputStream is = AbstractTestCRLUtils.class.getResourceAsStream("/notaires2020.arl");
				InputStream isCer = AbstractTestCRLUtils.class.getResourceAsStream("/citizen_ca.cer")) {

			CertificateToken certificateToken = loadCert(isCer);

			CRLBinary crlBinary = CRLUtils.buildCRLBinary(toByteArray(is));
			CRLValidity validity = CRLUtils.buildCRLValidity(crlBinary, certificateToken);
			assertNotNull(validity);
			assertNotNull(validity.getThisUpdate());
			assertNotNull(validity.getNextUpdate());
			assertNotNull(validity.getSignatureAlgorithm());
		}
	}

	// @Ignore
	@Test
	public void testHugeCRL() throws Exception {
		try (InputStream is = AbstractTestCRLUtils.class.getResourceAsStream("/esteid2011.crl");
				InputStream isCer = AbstractTestCRLUtils.class.getResourceAsStream("/ESTEID-SK_2011.der.crt")) {

			CertificateToken certificateToken = loadCert(isCer);

			CRLBinary crlBinary = CRLUtils.buildCRLBinary(toByteArray(is));
			CRLValidity validity = CRLUtils.buildCRLValidity(crlBinary, certificateToken);

			assertEquals(SignatureAlgorithm.RSA_SHA256, validity.getSignatureAlgorithm());
			assertNotNull(validity.getThisUpdate());
			assertNotNull(validity.getNextUpdate());
			assertNull(validity.getExpiredCertsOnCRL());
			assertNotNull(validity.getIssuerToken());
			assertTrue(validity.isValid());

			BigInteger serialNumber = new BigInteger("1111111111111111111");
			assertNull(CRLUtils.getRevocationInfo(validity, serialNumber));
		}
	}

	@Test
	public void testRealNot() throws Exception {
		try (InputStream is = AbstractTestCRLUtils.class.getResourceAsStream("/realts2019.crl");
				InputStream isCer = AbstractTestCRLUtils.class.getResourceAsStream("/realts2019.crt")) {
			CertificateToken certificateToken = loadCert(isCer);
			CRLBinary crlBinary = CRLUtils.buildCRLBinary(toByteArray(is));
			CRLValidity wrongIssuerCRL = CRLUtils.buildCRLValidity(crlBinary, certificateToken);

			assertNotNull(wrongIssuerCRL);
			assertNull(wrongIssuerCRL.getIssuerToken());
			assertNotNull(wrongIssuerCRL.getThisUpdate());
			assertNotNull(wrongIssuerCRL.getNextUpdate());
			assertTrue(wrongIssuerCRL.isIssuerX509PrincipalMatches());
			assertNotNull(wrongIssuerCRL.getSignatureInvalidityReason());
			assertFalse(wrongIssuerCRL.isValid());
			assertEquals(SignatureAlgorithm.RSA_SHA256, wrongIssuerCRL.getSignatureAlgorithm());
		}
	}

	@Test
	public void testECDSA() throws Exception {
		try (InputStream is = AbstractTestCRLUtils.class.getResourceAsStream("/EE-GovCA2018.crl");
				InputStream isCer = AbstractTestCRLUtils.class.getResourceAsStream("/EE-GovCA2018.pem.crt")) {

			CertificateToken certificateToken = loadCert(isCer);

			CRLBinary crlBinary = CRLUtils.buildCRLBinary(toByteArray(is));
			CRLValidity validity = CRLUtils.buildCRLValidity(crlBinary, certificateToken);

			assertEquals(SignatureAlgorithm.ECDSA_SHA512, validity.getSignatureAlgorithm());
			assertNotNull(validity.getThisUpdate());
			assertNotNull(validity.getNextUpdate());
			assertNull(validity.getExpiredCertsOnCRL());
			assertNotNull(validity.getIssuerToken());
			assertTrue(validity.isValid());
		}
	}

	@Test
	public void testECDSAwithRSACert() throws Exception {
		try (InputStream is = AbstractTestCRLUtils.class.getResourceAsStream("/EE-GovCA2018.crl");
				InputStream isCer = AbstractTestCRLUtils.class.getResourceAsStream("/citizen_ca.cer")) {

			CertificateToken certificateToken = loadCert(isCer);

			CRLBinary crlBinary = CRLUtils.buildCRLBinary(toByteArray(is));
			CRLValidity validity = CRLUtils.buildCRLValidity(crlBinary, certificateToken);

			assertEquals(SignatureAlgorithm.ECDSA_SHA512, validity.getSignatureAlgorithm());
			assertNotNull(validity.getThisUpdate());
			assertNotNull(validity.getNextUpdate());
			assertNull(validity.getExpiredCertsOnCRL());
			assertNull(validity.getIssuerToken());
			assertFalse(validity.isValid());
		}
	}

	@Test
	@DisabledForJreRange(min = JRE.JAVA_16)
	public void testPSSwithoutBouncyCastle() throws Exception {
		try (InputStream is = AbstractTestCRLUtils.class.getResourceAsStream("/d-trust_root_ca_1_2017.crl");
				InputStream isCer = AbstractTestCRLUtils.class.getResourceAsStream("/D-TRUST_Root_CA_1_2017.crt")) {
			Exception exception = assertThrows(IllegalArgumentException.class, () -> loadCert(isCer));
			assertEquals("Unable to initialize PSS", exception.getMessage());
		}
	}

	@Test
	@DisabledForJreRange(max = JRE.JAVA_15)
	public void testPSSwithoutBouncyCastleBeforeJDK16() throws Exception {
		try (InputStream is = AbstractTestCRLUtils.class.getResourceAsStream("/d-trust_root_ca_1_2017.crl");
			 InputStream isCer = AbstractTestCRLUtils.class.getResourceAsStream("/D-TRUST_Root_CA_1_2017.crt")) {
			assertNotNull(loadCert(isCer));
		}
	}

	@Test
	public void incompleteCRL() throws Exception {
		try (InputStream is = new ByteArrayInputStream(new byte[] { 1, 2, 3 })) {
{'fraction_non_alphanumeric': 0.10571998159791443, 'fraction_numerical': 0.018708786995859532, 'mean_word_length': 6.444292237442922, 'pattern_counts': {'":': 0, '<': 3, '<?xml version=': 0, '>': 5, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 4, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '832532', 'n_tokens_mistral': 11399, 'n_tokens_neox': 9933, 'n_words': 1541}