Configuring OpenSSL

Create OpenSSL configuration file

This example was done with Ubuntu and Debian servers; for Red Hat and CentOS the path to Apache files is different.

On Ubuntu and Debian the Apache path is /etc/apache2; on Red Hat and CentOS it is /etc/httpd.

Edit file /etc/ssl/openssl.cnf

$ vim /etc/ssl/openssl.cnf

    RANDFILE         = $ENV::SSLDIR/.rnd
 
    [ ca ]
    default_ca       = CA_default
 
    [ CA_default ]
    dir              = /opt/ca
    certs            = $dir/certs
    new_certs_dir    = $dir/newcerts
    crl_dir          = $dir/crl
    database         = $dir/index.txt
    private_key      = $dir/private/ca.key
    certificate      = $dir/ca.crt
    serial           = $dir/serial
    crl              = $dir/crl.pem
    RANDFILE         = $dir/private/.rand
    default_days     = 365
    default_crl_days = 30
    default_md       = sha1
    preserve         = no
    policy           = policy_anything
    name_opt         = ca_default
    cert_opt         = ca_default
 
    [ policy_anything ]
    countryName             = optional
    stateOrProvinceName     = optional
    localityName            = optional
    organizationName        = optional
    organizationalUnitName  = optional
    commonName              = supplied
    emailAddress            = optional
 
    [ req ]
    default_bits            = 2048
    default_md              = sha1
    default_keyfile         = privkey.pem
    distinguished_name      = req_distinguished_name
    x509_extensions         = v3_ca
    string_mask             = nombstr
 
    [ req_distinguished_name ]
    countryName             = Country Name (2 letter code)
    countryName_min         = 2
    countryName_max         = 2
    stateOrProvinceName     = State or Province Name (full name)
    localityName            = Locality Name (eg, city)
    0.organizationName      = Organization Name (eg, company)
    organizationalUnitName  = Organizational Unit Name (eg, section)
    commonName              = Common Name (eg, YOUR name)
    commonName_max          = 64
    emailAddress            = Email Address
    emailAddress_max        = 64
 
    [ usr_cert ]
    basicConstraints        = CA:FALSE
    # nsCaRevocationUrl       = https://url-to-exposed-clr-list/crl.pem
 
    [ ssl_server ]
    basicConstraints        = CA:FALSE
    nsCertType              = server
    keyUsage                = digitalSignature, keyEncipherment
    extendedKeyUsage        = serverAuth, nsSGC, msSGC
    nsComment               = "OpenSSL Certificate for SSL Web Server"
 
    [ ssl_client ]
    basicConstraints        = CA:FALSE
    nsCertType              = client
    keyUsage                = digitalSignature, keyEncipherment
    extendedKeyUsage        = clientAuth
    nsComment               = "OpenSSL Certificate for SSL Client"
 
    [ v3_req ]
    basicConstraints       = CA:FALSE
    keyUsage               = nonRepudiation, digitalSignature, keyEncipherment
 
    [ v3_ca ]
    basicConstraints        = critical, CA:true, pathlen:0
    nsCertType              = sslCA
    keyUsage                = cRLSign, keyCertSign
    extendedKeyUsage        = serverAuth, clientAuth
    nsComment               = "OpenSSL CA Certificate"
 
    [ crl_ext ]
    basicConstraints        = CA:FALSE
    keyUsage                = digitalSignature, keyEncipherment
    nsComment               = "OpenSSL generated CRL"

Create Certification Authority (CA)

Create folder structure to hold certificates:

$ mkdir /opt/met-ca
$ mkdir /opt/met-ca/certs
$ mkdir /opt/met-ca/crl
$ mkdir /opt/met-ca/newcerts
$ mkdir /opt/met-ca/private
$ mkdir /opt/met-ca/requests
$ touch /opt/met-ca/index.txt
$ echo “01” > /opt/ca/serial
$ echo “01” > /opt/ca/crlnumber
$ chmod 700 /opt/ca

Create public and private self-signed keys for our own Certification Authority (in the example they are valid for 10 years). We will need to specify certificate data and a password to encrypt, and the process will generate two files:

$ openssl req -config /etc/ssl/openssl.cnf -new -x509 -days 3650 -sha1 -newkey rsa:2048 -keyout /opt/ca/private/ca.key -out /opt/ca/ca.crt

Change key permissions:

$ chmod 600 /opt/met-ca/private/ca.key

Create Apache certificate 

Create a pair of keys. You will need to specify a password and certificate data. This will create the key file (server.key) and a certificate request (server.pem).

$ openssl req -new -sha1 -newkey rsa:2048 -nodes -keyout server.key -out server.pem

The CA should sign the certificate request. Copy server.pem to the requests directory and sign it.

$ openssl ca -config /etc/ssl/openssl.cnf -policy policy_anything -extensions ssl_server -out requests/server-signed.pem -infiles requests/server.pem

Apache expects PEM format; it is mandatory to convert to this format:

$ openssl x509 -in requests/server-signed.pem -out requests/server.crt

Apache configuration

Copy server.crt and server.key into /etc/apache2/ssl (if the SSL folder does not exist, create it). Change file permissions (server.key should be readable only by the root user; server.crt should be readable by everyone):

$ chmod 400 server.key
$ chmod 444 server.crt

If Apache is not listening on the SSL port, enable it by configuring /etc/apache2/ports.conf:

Listen 80
Listen 443 

Enable Apache SSL support:

$ apt-get install libapache-mod-ssl

Tell Apache to load SSL modules:

$ a2enmod ssl

Configure website:

Link the default-ssl file to enable SSL:

$ ln -s /etc/apache2/sites-available/default-ssl /etc/apache2/sites-enabled/default-ssl

Edit /etc/apache2/sites-available/default-ssl (enable the SSL engine and set SSLCertificateFile and SSLCertificateKeyFile)

SSLEngine on
SSLCertificateFile /etc/apache2/ssl/server.crt
SSLCertificateKeyFile /etc/apache2/ssl/server.key

Create user certificate:

To create certificates and sign them with the CA, first create the pair of keys. You will need to specify a password and certificate data. This will create a key (user.key) and a certificate request (user.pem):

$ openssl req -new -sha1 -newkey rsa:2048 -nodes -keyout user.key -out user.pem

With the CA, you need to sign certificates:

$ cp /tmp/usuario.pem /opt/ca/requests
$ openssl ca -config /etc/ssl/openssl.cnf -policy policy_anything -extensions [b]ssl_client[/b] -out requests/user-signed.pem -infiles requests/user.pem

Convert the certificate to PKCS#12 to be recognized by the browser  

$ openssl pkcs12 -export -clcerts -in user-signed.pem -inkey usuario.key -out user.p12

The files user-signed.pem, user.pem and user.key can be deleted  

$ wipe user-signed.pem user.key user.pem

The user.p12 should be installed in the user's browser.

Certificate revocation

If the server has been compromised, the certificate should be revoked by the CA. To revoke a certificate, check the serial number at /opt/ca/index.txt.  

$ openssl ca -config /etc/ssl/openssl.cnf -revoke newcerts/<serial-number>.pem

Create a list of revoked certificates (CRL)

$ openssl ca -config /etc/ssl/openssl.cnf -gencrl -crlexts crl_ext -md sha1 -out crl.pem

To send the list to the browser, it should be converted to DER format:  

$ openssl crl -in crl.pem -out ca.crl -outform DER

It can now be sent to the browser.

Add CRL to Apache

Copy the CRL file to the Apache SSL folder:  

$ cp /tmp/crl.pem /etc/apache2/ssl/ca.crl

Modify /etc/apache2/sites-available/default-ssl file and add SSLCARevocationFile:

SSLCARevocationFile /etc/apache2/ssl/ca.crl

Restart the Apache service.