Create a chain of self signed certificates

Note, update: This has a follow up post for the case where you want to keep any Subject Alternativ Name (SAN) fields in the certificate to sign.

On occasion, I’ve needed to create my own self-signed SSL-certificates for various testing purposes. At work today I needed a certificate that was signed by another certificate, i.e. I needed a chain of trusted certificates for testing, where the cert at the top of the chain is used as a trusted root certificate. The premise is is simple: If you trust the root certificate, you should also trust the certificates further down in the chain, since they are signed using the trusted certificate.

I generally work on a Windows system, but for certain tasks such as this, I often find Unix-style tools preferable. Luckily, if you used the Git Bash command line for windows and have OpenSSL included, you’ll have everything you need right there. This post provides a few quick steps needed to create such a chain of trusted certificates using OpenSSL.

Step 1: Define a Certificate Authority (CA)

Create a plain text file with the following content, and save it as e.g. CertAuth.conf:

[ ca ]
default_ca = ca_default
[ ca_default ]
dir = ./certauth
certs = $dir
new_certs_dir = $dir/certs
database = $dir/db
serial = $dir/serial
RANDFILE = $dir/rand
certificate = $dir/ca.crt
private_key = $dir/ca.key
default_days = 365
default_crl_days = 30
default_md = md5
preserve = no
policy = generic_policy
[ generic_policy ]
countryName = optional
stateOrProvinceName = optional
localityName = optional
organizationName = optional
organizationalUnitName = optional
commonName = optional
emailAddress = optional

Step 2: Add required files to the certauth directory

Create a directory certauth (corresponding to $dir in the script above). This is where files needed by the CA will be placed.

mkdir certauth

Under certauth, create a directory certs, an index-file index, and a database file, db:

cd certauth
mkdir certs
touch index
touch db

Step 3: Create a private key and a certificate for the CA

Create a 1024-bit RSA key for the certificate authority you just defined (from the bash command line while in the ca directory). This will ask you to choose (and confirm) a password for the key.

openssl genrsa -des3 -out ca.key 2048

…and then use that key to sign a certificate. You’ll need to provide the password the password you chose previously now, in order to use the key you just created, and enter some data about the certificate (country, region, organization name, etc. – you can leave some of these blank if you like).

openssl req -new -x509 -days 10000 -key ca.key -out ca.crt

Step 4: Create a Certificate Signing Request

Now that the CA and root cert is ready, we can create a request for a certificate is signed by the root cert created above. First, create a file similar to the following example, and save it as signreq.req in the outer directory (not under certauth). NOTE: Be sure to save this in ANSI, to avoid any encoding errors:

default_bits = 2048
prompt = no
default_md = sha256
x509_extensions = v3_req
distinguished_name = dn
C = NO
O = Acme Security Industries Ltd
CN = My Dummy Cert

…then generate the request based on that file; this will generate the request as myreq.pem, and a corresponding private key as mykey.key:

openssl req -new -newkey rsa:2048 -nodes -keyout mykey.key -out myreq.pem -config signreq.req

Step 5: Generate the signed cert based on the request, using the CA

Finally, let’s generate the signed certificate based on the recently created request, using the previously created CA. This includes -create_serial in order to generate a random number / id for the cert, which is stored in the CA along with other basic info about the cert.

You’ll be asked for the password again here, and then requested to confirm the signing of the certificate for the given period, and then to commit the signing.

openssl ca -config certauth.conf -create_serial -out certificate.crt -infiles myreq.pem

That should provide you with a signed certificate called certificate.crt. If you open it however, you’ll see the following status, and see a warning icon over the cert. Why is this? Simple: You haven’t imported the root certificate yet.

Post-step: Import the dummy root cert

Go into the certauth folder and locate the cert you intend to use as a root cert; ca.crt. If you open it, you’ll see that it is untrusted:

Click Install Certificate to install it, and select Trusted Root Certificates as the place to store it. Be careful doing this of course – you don’t want to accidentally trust ant certificates that are not really trustworthy. In fact, I’d recommend removing the certificate from here once you’re done testing, even if only to keep things clean and tidy.

Now that you have chosen to trust the root certificate, you can once again open both certificates and have a look: The root cert should be trusted directly, and the other one (which was signed using the root cert) should be trusted indirectly via its certification path / trust chain:

4 thoughts on “Create a chain of self signed certificates

Engage and contribute for the common benefit of mankind!

This site uses Akismet to reduce spam. Learn how your comment data is processed.