Creating your own Certificate Authority

Reading time ~4 minutes

Creating your own Certificate Authority and certs

Often its useful to create your own certificates for your own local network. Let’s go through the process of generating and signing certificates that can be trusted by your own machines.

First let’s create a location for storing CA information. We will use $HOME/certs for these examples and boomerain will be our example organization.

Creating our Certificate Authority

  1. We’ll first create a location for storing CA information. We will use $HOME/certs for these examples and boomerain will be our example organization.

    mkdir -p ~/certs
    cd ~/certs

  2. Create the CA private key. Keep this key and password safe!

    openssl genrsa -des3 -out boomerain.CA.key 2048

  3. Create a certificate signing request

    openssl req -verbose -new -key boomerain.CA.key -out boomerain.CA.csr -sha256
    > Country Name (2 letter code) [AU]:US
    > State or Province Name (full name) [Some-State]:New Jersey
    > Locality Name (eg, city) []:Lumberton
    > Organization Name (eg, company) [Internet Widgits Pty Ltd]:Boomerain
    > Organizational Unit Name (eg, section) []:
    > Common Name (e.g. server FQDN or YOUR name) []:CA for boomerain
    > Email Address []:<my email>

  4. Setup the CA configuration file. Create a file ca.conf with the following contents. This information is used with our CA signs requests.

     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    
    # we use 'ca' as the default section because we're usign the ca command
    [ ca ]
    default_ca = boomerain
    
    [ boomerain ]
    #  a text file containing the next serial number to use in hex. Mandatory.
    #  This file must be present and contain a valid serial number.
    serial = ./serial
    
    # the text database file to use. Mandatory. This file must be present though
    # initially it will be empty.
    database = ./index.txt
    
    # specifies the directory where new certificates will be placed. Mandatory.
    new_certs_dir = ./newcerts
    
    # the file containing the CA certificate. Mandatory
    certificate = ./boomerain.CA.crt
    
    # the file contaning the CA private key. Mandatory
    private_key = ./boomerain.CA.key
    
    # the message digest algorithm. Remember to not use MD5
    default_md = sha256
    
    # for how many days will the signed certificate be valid (10yrs)
    default_days = 3650
    
    # a section with a set of variables corresponding to DN fields
    policy = same_country
    
    [ same_country ]
    # if the value is "match" then the field value must match the same field in the
    # CA certificate. If the value is "supplied" then it must be present.
    # Optional means it may be present. Any fields not mentioned are silently
    # deleted.
    countryName = match
    stateOrProvinceName = supplied
    organizationName = supplied
    commonName = supplied
    organizationalUnitName = optional
    commonName = supplied

  5. Create an CA extensions file boomerain.CA.extensions.conf with This sets up the permissions of what the CA cert is allowed to do.

    1
    2
    3
    4
    5
    6
    7
    8
    
    basicConstraints=critical,@bs_section
    keyUsage=critical, keyCertSign, cRLSign
    extendedKeyUsage=emailProtection, serverAuth, clientAuth, timeStamping, msEFS, msCodeCom
    subjectKeyIdentifier = hash
    
    [ bs_section ]
    CA=true
    pathlen=1

  6. Setup the dir for signing.

    • Newly signed certs will be kept in newcerts.
    • index.txt will be tracking our signed certs and be used for revoking
    • serial keeps track of the number of the next cert to sign
      mkdir newcerts
      touch index.txt
      echo "01" > serial
  7. Sign your CA’s cert

    openssl ca -config ca.conf \
               -extfile boomerain.CA.extensions.conf \
               -out boomerain.CA.crt \
               -keyfile boomerain.CA.key \
               -verbose -selfsign -md sha256 \
               -enddate 210001010000Z \
               -infiles boomerain.CA.csr

Create certificates

Next we want to generate certificates that we will use. We will use $CERT_NAME for our new cert.

export CERT_NAME=<my_new_cert_name>

  1. Generate a certificate key. Don’t use a password here if you want to use with nginx, apache, etc.

    openssl genrsa -out $CERT_NAME.key 2048

  2. Next generate a signing request that our CA will use to sign our cert: I’m using .home here as my local network domain.

     1
     2
     3
     4
     5
     6
     7
     8
     9
    10
    11
    
    openssl req -verbose -new -key $CERT_NAME.key -out $CERT_NAME.csr -sha256
    
    echo "basicConstraints=CA:FALSE
    keyUsage = keyEncipherment, dataEncipherment
    extendedKeyUsage = serverAuth, clientAuth
    subjectAltName=@alt_names
    subjectKeyIdentifier = hash
    
    [ alt_names ]
    DNS.1 = *.home
    DNS.2 = home" > $CERT_NAME.extensions.conf

  3. Sign our request with our CA:

        openssl ca -config ca.conf -extfile $CERT_NAME.extensions.conf -out $CERT_NAME.pem -keyfile boomerain.CA.key -infiles $CERT_NAME.csr
        # Optional util I wrote for combining the CA cert and newly signed cert
        makechain $CERT_NAME.pem boomerain.CA.crt > $CERT_NAME.fullchain.pem

comments powered by Disqus