Some of my (and others) notes of managing PKI with the excellent
openssl. Its simple and just works. To get going will create a root CA (Certificate Authority) and an intermediate signing CA. Using the CA’s will issue three keypairs; one for email protection, one for TLS, and one for digital signatures. The digital signature keypair will be presented in the form of a CSR (Certificate Signing Request), as if generated by a third party that would like a keypair, signed by our CA hierarchy.
- Create the Root CA
- Create the Intermediate CA
- Create Working Certificates
- Output Formats
- Viewing Artifacts
- Configuration Files
- Key usage extensions
Create the Root CA
First setup a neat directory tree, to keep things clear.
mkdir -p ca/root-ca/private ca/root-ca/db crl certs chmod 700 ca/root-ca/private
Create the various CA database files, which must exist prior to using the
openssl ca command. These are all referenced in the configuration file passed in to
openssl, which we’ll see shortly.
touch ca/root-ca/db/root-ca.db ca/root-ca/db/root-ca.db.attr echo 01 > ca/root-ca/db/root-ca.crt.srl echo 01 > ca/root-ca/db/root-ca.crl.srl
After this setup, should have a similar directory tree to this:
. ├── ca │ └── root-ca │ ├── db │ │ ├── root-ca.db │ │ └── root-ca.db.attr │ └── private ├── certs ├── crl ├── email.conf ├── root-ca.conf ├── server.conf └── signing-ca.conf
The Request (CSR)
Start by producing a new keypair, in the form of a Certificate Signing Request (CSR). A CSR, breaks out the private and public keys, so you can provide just the public key portion to another trusted party for signing. Once signed, and now part of a trust chain, you can combine the two pieces together again.
openssl req -new -config root-ca.conf -out ca/root-ca.csr -keyout ca/root-ca/private/root-ca.key
Refer to root-ca.conf below.
ca command, can now issue a root CA based on the CSR. The root certificate is self signed, and is the base of all trust relationships in the PKI.
openssl ca -selfsign -config root-ca.conf -in ca/root-ca.csr -out ca/root-ca.crt -extensions root_ca_ext
Create the Intermediate CA
A very similar procedure for the root CA. Some setup:
mkdir -p ca/signing-ca/private ca/signing-ca/db crl certs chmod 700 ca/signing-ca/private
And the the files (databases) themselves:
touch ca/signing-ca/db/signing-ca.db ca/signing-ca/db/signing-ca.db.attr echo 01 > ca/signing-ca/db/signing-ca.crt.srl echo 01 > ca/signing-ca/db/signing-ca.crl.srl
The Request (CSR)
As for the root CA, spawn a new keypair in the form of a CSR:
openssl req -new -config signing-ca.conf -out ca/signing-ca.csr -keyout ca/signing-ca/private/signing-ca.key
Refer to signing-ca.conf below.
Again use the
ca command to issue a certificate based on a CSR.
openssl ca -config root-ca.conf -in ca/signing-ca.csr -out ca/signing-ca.crt -extensions signing_ca_ext
- Configure against the root CA
root-ca.conf, which is signing the intermediate signing CA CSR.
signing_ca_extextension is used, as opposed to the
root_ca_extused earlier, and is defined as a section in
[ signing_ca_ext ] keyUsage = critical,keyCertSign,cRLSign basicConstraints = critical,CA:true,pathlen:0 subjectKeyIdentifier = hash authorityKeyIdentifier = keyid:always
Create Working Certificates
Email Protection Certificate
The Request (CSR)
req -new command to create a new keypair (in the form of a CSR).
openssl req -new -config email.conf -out certs/ben-email.csr -keyout certs/ben-email.key Generating a 2048 bit RSA private key ..+++ .............+++ writing new private key to 'certs/ben-email.key' Enter PEM pass phrase: Verifying - Enter PEM pass phrase: ----- You are about to be asked to enter information that will be incorporated into your certificate request. What you are about to enter is what is called a Distinguished Name or a DN. There are quite a few fields but you can leave some blank For some fields there will be a default value, If you enter '.', the field will be left blank. ----- 1. Domain Component (DC=net) :DC=net 2. Domain Component (DC=bencode) :DC=bencode 3. Domain Component (DC=pki) :DC=pki 4. Organization Name (O=bEncode Labs) :O=bEncode Labs 5. Organizational Unit Name (OU=section) : 6. Common Name (CN=Benjamin Simmonds) :CN=Benjamin Simmonds 7. Email Address (emailAddressfirstname.lastname@example.org) :emailAddressemail@example.com
Refer to email.conf below.
Here’s where it all comes together. Given the email CSR from above, will now attempt sign it using the Intermediate Signing CA that was setup earlier.
openssl ca -config signing-ca.conf -in certs/ben-email.csr -out certs/ben-email.crt -extensions email_ext
Note that the signing CA config
signing-ca.conf is used.
email_ext is defined as a section in
signing-ca.conf as follows, which stamps the certificate with certain usage properties relating to email validation and signing.
[ email_ext ] keyUsage = critical,digitalSignature,keyEncipherment basicConstraints = CA:false extendedKeyUsage = emailProtection,clientAuth subjectKeyIdentifier = hash authorityKeyIdentifier = keyid:always
TLS Server Certificate
The Request (CSR)
Almost identical, but with some different usage properties. Note you can read environment variables within the OpenSSL configuration for example
$ENV::SAN reads the
SAN=DNS:www.bencode.net openssl req -new -config tls-server.conf -out certs/bencode.net.csr -keyout certs/bencode.net.key
Refer to tls-server.conf below.
Use the signing CA to issue the TLS server certificate.
openssl ca -config signing-ca.conf -in certs/bencode.net.csr -out certs/bencode.net.crt -extensions server_ext
OpenSSL supports a range of standard formats, including DER and PKCS#7 and PKCS#12 (standards based version of Microsoft’s PFX).
DER (RFC2585) Certificate
openssl x509 -in certs/ben-email.crt -out certs/ben-email.cer -outform der
DER (RFC2585) CRL (Revocation List)
gencrl command to create a CRL, that is all revoked, but not yet expired certificates.
Tip: A new CRL must be generated at regular intervals.
openssl ca -gencrl -config signing-ca.conf -out crl/signing-ca.crl cat crl/signing-ca.crl -----BEGIN X509 CRL----- MIICBDCB7QIBATANBgkqhkiG9w0BAQUFADCBiTETMBEGCgmSJomT8ixkARkWA25l dDEXMBUGCgmSJomT8ixkARkWB2JlbmNvZGUxFTATBgNVBAoMDGJFbmNvZGUgTGFi ...
This can be converted to DER by:
openssl crl -in crl/signing-ca.crl -out crl/signing-ca.crl -outform der cat crl/signing-ca.crl 0��10H�� ...
PKCS#12 (p12) Bundle
A standards, cleaned up version of Microsofts PFX format. Typically used for bundling a certificate and its private key. Additional certificates (e.g. those needed to build the trust chain up to the Root CA) can be included. For example:
cat ca/signing-ca.crt ca/root-ca.crt certs/ben-email.crt > certs/ben-email-with-chain.pem openssl pkcs12 -export -name "Ben Simmonds" -inkey certs/ben-email.key -in certs/ben-email-with-chain.pem -out certs/ben-email.p12 Enter pass phrase for certs/ben-email.key: Enter Export Password: Verifying - Enter Export Password:
Super simple. Involves concatenating other PEM formatted files together. This could be the trust chain certificates, or the private key and its certificate, or the private key its certificate and the trust chain certificates, or any other combination.
The trust chain of CA certificates:
cat ca/signing-ca.crt ca/root-ca.crt > ca/signing-ca-chain.pem
The private key and certificate:
cat certs/ben-email.key certs/ben-email.crt > certs/ben-email.pem
CSR (Signing Request)
openssl req -in certs/ben-email.csr -noout -text
openssl x509 -in certs/ben-email.cer -noout -text -inform der
CRL (Revocation List)
openssl crl -in crl/signing-ca.crl -inform der -noout -text
openssl pkcs12 -in certs/ben-email.p12 -nodes -info Enter Import Password: MAC:sha1 Iteration 2048 PKCS7 Encrypted data: pbeWithSHA1And40BitRC2-CBC, Iteration 2048 Certificate bag Bag Attributes localKeyID: 4E CB 73 0B 90 E7 A4 6E 15 27 BD 3B B7 03 33 1A 8A C9 CF 88 friendlyName: Ben Simmonds subject=/DC=net/DC=bencode/O=bEncode Labs/CN=Benjamin Simmonds issuer=/DC=net/DC=bencode/O=bEncode Labs/OU=bEncode Labs Signing CA/CN=bEncode Labs Signing CA -----BEGIN CERTIFICATE----- MIIEADCCAuigAwIBAgIBATANBgkqhkiG9w0BAQUFADCBiTETMBEGCgmSJomT8ixk
Key usage extensions
|Key usage extension||Description|
|Digital signature||Use when the public key is used with a digital signature mechanism to support security services other than non-repudiation, certificate signing, or CRL signing. A digital signature is often used for entity authentication and data origin authentication with integrity.|
|Non-repudiation||Use when the public key is used to verify digital signatures used to provide a non-repudiation service. Non-repudiation protects against the signing entity falsely denying some action (excluding certificate or CRL signing).|
|Key encipherment||Use when a certificate will be used with a protocol that encrypts keys. An example is S/MIME enveloping, where a fast (symmetric) key is encrypted with the public key from the certificate. SSL protocol also performs key encipherment.|
|Data encipherment||Use when the public key is used for encrypting user data, other than cryptographic keys.|
|Key agreement||Use when the sender and receiver of the public key need to derive the key without using encryption. This key can then can be used to encrypt messages between the sender and receiver. Key agreement is typically used with Diffie-Hellman ciphers.|
|Certificate signing||Use when the subject public key is used to verify a signature on certificates. This extension can be used only in CA certificates.|
|CRL signing||Use when the subject public key is to verify a signature on revocation information, such as a CRL.|
|Encipher only||Use only when key agreement is also enabled. This enables the public key to be used only for enciphering data while performing key agreement.|
|Decipher only||Use only when key agreement is also enabled. This enables the public key to be used only for deciphering data while performing key agreement.|
Digital Signatures - how they work
This does have an XML flavour to it.
To validate (i.e. to prove)
- First the message can be normalised, and in the case of XML will use something like the “Exclusive XML Canonicalization” (XML-C14N), so we’re comparing apples with apples. This will disgard things like usage of white space.
- Using the normalised representation, compute a hash (e.g. SHA1) of the timestamp (contained WS-Security header) and entire message payload (the SOAP body).
- Using the public key from the partner organisation certificate, RSA decrypt the hash computed by partner organisation.
- If the two hashes are identical, we know the message has not been tampered with.
- (optional) Validate the timestampt (TTL) defined by partner organisation (typically 7 minutes).
To sign (i.e. to create)
- Wraps the response message in a SOAP envelope, which includes some WS-Security related headers including a timestamp.
- The timestamp is set to a configurable number of minutes (e.g. 10 minutes) in the future.
- Normalises the message using the “Exclusive XML Canonicalization” (XML-C14N)
- Using the noramlised message, computes a (e.g. SHA1) hash of the timestamp (WS-Security header) and entire response message payload (e.g. the SOAP body).
- Uses the private key of signing certificate, RSA signs the computed hash, and stores the result in the relevant security header (the SignatureValue header).
- The message is then delivered to partner organisation.