Ejemplo n.º 1
0
/**
 * Verify the ocsp status of a certificate
 */
cert_status_t verify_by_ocsp(const cert_t *cert, time_t *until,
							 time_t *revocationDate,
							 crl_reason_t *revocationReason)
{
	x509_t *x509 = (x509_t*)cert->cert;
	chunk_t serialNumber = x509->get_serial(x509);
	cert_status_t status;
	ocsp_location_t location;
	time_t nextUpdate = UNDEFINED_TIME;

	*revocationDate = UNDEFINED_TIME;
	*revocationReason = CRL_REASON_UNSPECIFIED;

	/* is an ocsp location defined? */
	if (!build_ocsp_location(cert, &location))
	{
		return CERT_UNDEFINED;
	}

	lock_ocsp_cache("verify_by_ocsp");
	status = get_ocsp_status(&location, serialNumber, &nextUpdate
		, revocationDate, revocationReason);
	unlock_ocsp_cache("verify_by_ocsp");

	if (status == CERT_UNDEFINED || nextUpdate < time(NULL))
	{
		plog("ocsp status is stale or not in cache");
		add_ocsp_fetch_request(&location, serialNumber);

		/* inititate fetching of ocsp status */
		wake_fetch_thread("verify_by_ocsp");
	}
	*until = nextUpdate;
	return status;
}
Ejemplo n.º 2
0
/*
 * verify the ocsp status of a certificate
 */
bool
verify_by_ocsp(/*const*/ x509cert_t *cert, bool strict, time_t *until)
{
    u_char status;
    ocsp_location_t location;
    time_t nextUpdate = 0;

    /* is an ocsp location defined? */
    if (!build_ocsp_location(cert, &location))
	return FALSE;

    lock_ocsp_cache("verify_by_ocsp");
    status = get_ocsp_status(&location, cert->serialNumber, &nextUpdate);
    unlock_ocsp_cache("verify_by_ocsp");

#ifdef HAVE_THREADS
    if (status == CERT_UNDEFINED || nextUpdate < time(NULL))
    {
	openswan_log("ocsp status is stale or not in cache");
	add_ocsp_fetch_request(&location, cert->serialNumber);

	/* inititate fetching of ocsp status */
	wake_fetch_thread("verify_by_ocsp");
	return !strict;
    }
#endif
    
    switch (status)
    {
    case CERT_GOOD:
    	DBG(DBG_CONTROL,
	    DBG_log("certificate is good")
	)
	/* with strict crl policy the public key must have the
	 * same lifetime as the validity of the ocsp status
	 */
	if (strict && nextUpdate < *until)
	    *until = nextUpdate;
	break;
    case CERT_REVOKED:
	plog("certificate is revoked");
	remove_x509_public_key(cert);
	return FALSE;
    case CERT_UNKNOWN:
	plog("certificate status unkown");
	if (strict)
	{
	    remove_x509_public_key(cert);
	    return FALSE;
	}
	break;
    }
    return TRUE;
}
Ejemplo n.º 3
0
Archivo: x509.c Proyecto: mkj/libreswan
/*
 * verify if a cert hasn't been revoked by a crl
 */
static bool verify_by_crl(/*const*/ x509cert_t *cert, bool strict,
				    realtime_t *until)
{
	x509crl_t *crl;
	char ibuf[ASN1_BUF_LEN], cbuf[ASN1_BUF_LEN];

	lock_crl_list("verify_by_crl");
	crl = get_x509crl(cert->issuer, cert->authKeySerialNumber,
			  cert->authKeyID);

	dntoa(ibuf, ASN1_BUF_LEN, cert->issuer);

	if (crl == NULL) {
		unlock_crl_list("verify_by_crl");
		libreswan_log("no crl from issuer \"%s\" found (strict=%s)",
			      ibuf,
			      strict ? "yes" : "no");

#if defined(LIBCURL) || defined(LDAP_VER)
		if (cert->crlDistributionPoints != NULL) {
			add_crl_fetch_request(cert->issuer,
					      cert->crlDistributionPoints);
			wake_fetch_thread("verify_by_crl");
		}
#endif
		if (strict)
			return FALSE;
	} else {
		x509cert_t *issuer_cert;
		bool valid;

		DBG(DBG_X509,
		    DBG_log("issuer crl \"%s\" found", ibuf));

#if defined(LIBCURL) || defined(LDAP_VER)
		add_distribution_points(cert->crlDistributionPoints,
					&crl->distributionPoints);
#endif

		lock_authcert_list("verify_by_crl");

		issuer_cert = get_authcert(crl->issuer,
					   crl->authKeySerialNumber,
					   crl->authKeyID, AUTH_CA);
		dntoa(cbuf, ASN1_BUF_LEN, crl->issuer);
		valid = check_signature(crl->tbsCertList, crl->signature,
					crl->algorithm, issuer_cert);

		unlock_authcert_list("verify_by_crl");

		if (valid) {
			bool revoked_crl, expired_crl;

			DBG(DBG_X509,
			    DBG_log("valid crl signature on \"%s\"", cbuf));

			/* with strict crl policy the public key must have the same
			 * lifetime as the crl
			 */
			if (strict && realbefore(crl->nextUpdate, *until))
				*until = crl->nextUpdate;

			/* has the certificate been revoked? */
			revoked_crl = x509_check_revocation(crl,
							    cert->serialNumber);

			/* is the crl still valid? */
			expired_crl = realbefore(crl->nextUpdate, realnow());

			unlock_crl_list("verify_by_crl");

			if (expired_crl) {
				char tbuf[REALTIMETOA_BUF];

				libreswan_log(
					"crl update for \"%s\" is overdue since %s",
					cbuf,
					realtimetoa(crl->nextUpdate, TRUE,
						tbuf, sizeof(tbuf)));

#if defined(LIBCURL) || defined(LDAP_VER)
				/* try to fetch a crl update */
				if (cert->crlDistributionPoints != NULL) {
					add_crl_fetch_request(cert->issuer,
							      cert->crlDistributionPoints);
					wake_fetch_thread("verify_by_crl");
				}
#endif
			} else {
				DBG(DBG_X509,
				    DBG_log("crl is \"%s\" valid", cbuf));
			}

			if (revoked_crl || (strict && expired_crl)) {
				/* remove any cached public keys */
				remove_x509_public_key(cert);
				return FALSE;
			}
		} else {
			unlock_crl_list("verify_by_crl");
			libreswan_log("invalid crl signature on \"%s\"", cbuf);
			if (strict)
				return FALSE;
		}
	}
	return TRUE;
}