Overview of X.509 certificate verification -- SSLeay 0.9.0b -- January 1999

NAME

X.509 certificate verification overview

SYNOPSIS

#include "x509.h"
#include "x509_vfy.h"

DESCRIPTION

What does an application need to do in order to be able to verify the validity ofan X509 certificate, either one it has been presented by some remote client, or one that it has retrieved frmo another source?

Informally, it needs to register a list of ways to find certificates from disk, register a verification function (or use the default that this library provides), and call the verify function on the certificate.

If you are willing to use only the default lookup methods that this library provides, you can get away with something as simple as

X509_STORE *ctx=NULL;
X509_STORE_CTX csc;

ctx=X509_STORE_new();
X509_STORE_set_default_paths(ctx);
X509_STORE_CTX_init(&csc,ctx,x,NULL);
i=X509_verify_cert(&csc);
X509_STORE_CTX_cleanup(&csc);
if (i) ... /* ok*/
else ... /* not */

If you are using ssl-level routines you can do even less:

SSL_CTX *ctx=NULL;

ctx=SSL_CTX_NEW();
... (set cipher list and other goodies for ssl)
SSL_CTX_set_default_verify_paths(ctx);

Then when the verification is done during the SSL handshake the default verification routine is invoked automatically and all 509_STORE_CTX stuff is done for you.

Let's assume that you are not using the ssl-level routines. In that case, first you are creating a new X509_STOR, which is

typedef struct x509_store_st
{
        /* The following is a cache of trusted certs */
        int cache;      /* if true, stash any hits */

        LHASH *certs;   /* cached certs; */ 

        /* These are external lookup methods */
        STACK *get_cert_methods;/* X509_LOOKUP */

        int (*verify)();        /* called to verify a certificate */
        int (*verify_cb)();     /* error callback */

        CRYPTO_EX_DATA ex_data; /* for mutex */
        int references;
        int depth;              /* how deep to look */
}  X509_STORE;

When it is created, all subfields are set to be empty, 0, or NULL.

Next, you are calling X509_STORE_set_default_paths to adding X509_LOOKUP_file() and X509_LOOKUP_hash_dir() to the lookup methods used by this X509_STORE. X509_LOOKUP_file() allows you to look up a cert in a specific file; X509_LOOKUP_hash_dir allows you to look up a cert in a directory which has a pile of certificates, each named by hashing the subject name and converting the first four bytes to ascii; then a number is tacked on to the end to indicate whether it is the first, second, third... with the same starting name. For example, "c605ac92.0".

It also adds one directory to the list which will be searched; unless you change this, it is X509_CERT_DIR (defined in cryptlib.h as "/usr/local/ssl/certs").

Next you initialize the X509_STORE_CTX that will be used during the verification; it is just a temporary structure used to hold results of computations. The init function sets all the entries to 0 or empty or NULL, except for the certificate to be verified, which you have hopefully passed as the argument x.

Then you do the actual verify, using the nicely set-up ctx.

Clean up the ctx (free various things that have been allocated and clear sensitive data).

Finally, check the return code from the verify to see whether the result was good or not.

If you don't want to use the default methods, then you should read the rest of the documentation for this part of the library. You may want to add your own lookup methods, change the default certificate directory or other defaults, set a verify callback which is called when an error is encountered in verifying a certificate, or even add your own verification function.

You may want more detail on the default verification function or lookup methods; that is also provided.