331.1 - X.509 Certificates and Public Key Infrastructures
Key Knowledge Areas:
- Understand X.509 certificates, X.509 certificate lifecycle, X.509 certificate fields and X.509v3 certificate extensions
- Understand trust chains and public key infrastructures, including certificate transparency
- Generate and manage public and private keys
- Create, operate and secure a certification authority
- Request, sign and manage server and client certificates
- Revoke certificates and certification authorities
- Basic feature knowledge of Let’s Encrypt, ACME and certbot
- Basic feature knowledge of CFSSL
Partial list of the used files, terms and utilities:
- openssl (including relevant subcommands)
- OpenSSL configuration
- PEM, DER, PKCS
- CSR
- CRL
- OCSP
Terms
PEM, DER, PKCS
CSR
CRL
OCSP
online certificate status protocol
OCSP stapling
online certificate status protocol stapling
Files
OpenSSL configuration
/etc/pki/tls/openssl.cnf
Utilities
openssl
man 1 ca
man 1 openssl
man 1 genpkey
man 1 pkeyutl
man 1 req
Notes
Certificate Transparency
Certificate Authority
create root certificate:
- copy and update the configuration file:
# prepare root directory mkdir -p CA/{certs,crl,newcerts,private} chmod u=rwx,g=,o= CA/private # initialize files touch CA/index.txt printf 1000 > CA/crlnumber printf 1000 > CA/serial cp /etc/pki/tls/openssl.cnf CA/ # configure file paths section="$(sed -n '/^\[ ca \]$/,/\[/ s@^default_ca[ \t]*=[ \t]*@@p' CA/openssl.cnf | sed 's@[ \t]*#.*$@@')" sed -e "/^\[ $section \]$/,/^\[/ s@^dir\t\t=.*@dir\t\t= ./CA@" -i CA/openssl.cnf sed -e "/^\[ $section \]$/,/^\[/ s@^certificate\t=.*@certificate\t= \$dir/certs/cacert.pem@" -i CA/openssl.cnf sed -e "/^\[ $section \]$/,/^\[/ s@^crl\t\t=.*@crl\t\t= \$dir/crl/cacrl.pem@" -i CA/openssl.cnf # configure defaults for certificates to be issued sed -e "/^\[ $section \]$/,/^\[/ s@^x509_extensions\t=.*@x509_extensions\t= v3_intermediate_ca@" -i CA/openssl.cnf sed -e "/^\[ $section \]$/,/^\[/ s@^default_days\t=.*@default_days\t= 3650@" -i CA/openssl.cnf # configure v2 certificate revocation list support sed -e "/^\[ $section \]$/,/^\[/ s@^#[ \t]*crl_extensions[ \t]*=.*@crl_extensions\t= crl_ext@" -i CA/openssl.cnf # configure defaults for root certificate signing request sed -e '/^\[ req \]$/,/^\[/ s@^default_bits\t\t=.*@default_bits\t\t= 4096@' -i CA/openssl.cnf sed -e '/^\[ req \]$/,/^\[/ s@^default_keyfile[ \t]*=.*@default_keyfile\t= ./CA/private/cakey.pem@' -i CA/openssl.cnf sed -e '/^\[ v3_ca \]$/,/^\[/ s@^#[ \t]*keyUsage[ \t]*=.*@keyUsage = cRLSign, keyCertSign@' -i CA/openssl.cnf - configure CA for signing intermediate:
cat >> CA/openssl.cnf << EOF [ v3_intermediate_ca ] # Extensions for a typical intermediate CA (man x509v3_config). # PKIX recommendation. subjectKeyIdentifier = hash authorityKeyIdentifier = keyid:always,issuer basicConstraints = critical,CA:true,pathlen:0 keyUsage = cRLSign, keyCertSign # CRL and OCSP extensions # authorityInfoAccess = OCSP;URI:http://ocsp.example.net/ crlDistributionPoints = URI:http://example.net/cacrl.pem EOFNOTE:
basicConstraints = pathlen:0prevents the issued certificate from issuing another certificate authorityNOTE: OCSP is being phased out by Let’s Encrypt due to concerns regarding:
- privacy of end users
- resource use
- lack of support in web browsers for OCSP Must Staple extension, which addresses the other two concerns
- generate the root certificate and private key:
openssl req -config CA/openssl.cnf -days 7300 -new -newkey rsa -out CA/certs/cacert.pem -subj /C=CY/ST=ProvinceState/L=City/O=Organization/CN=ca-alpha.example.net -x509 - inspect the root certificate:
openssl x509 -dates -ext basicConstraints -in CA/certs/cacert.pem -issuer -noout -subject
create intermediate certificate
- copy and update the configuration file:
# prepare intermediate directory mkdir -p Intermediate/{certs,crl,csr,newcerts,private} chmod u=rwx,g=,o= Intermediate/private # initialize files touch Intermediate/index.txt printf 1000 > Intermediate/crlnumber printf 1000 > Intermediate/serial cp /etc/pki/tls/openssl.cnf Intermediate/ # configure file paths section="$(sed -n '/^\[ ca \]$/,/\[/ s@^default_ca[ \t]*=[ \t]*@@p' Intermediate/openssl.cnf | sed 's@[ \t]*#.*$@@')" sed -e "/^\[ $section \]$/,/^\[/ s@^dir\t\t=.*@dir\t\t= ./Intermediate@" -i Intermediate/openssl.cnf sed -e "/^\[ $section \]$/,/^\[/ s@^certificate\t=.*@certificate\t= \$dir/certs/intermediatecert.pem@" -i Intermediate/openssl.cnf sed -e "/^\[ $section \]$/,/^\[/ s@^crl\t\t=.*@crl\t\t= \$dir/crl/intermediatecrl.pem@" -i Intermediate/openssl.cnf sed -e "/^\[ $section \]$/,/^\[/ s@^private_key\t=.*@private_key\t= \$dir/private/intermediatekey.pem@" -i Intermediate/openssl.cnf # configure defaults for certificates to be issued sed -e "/^\[ $section \]$/,/^\[/ s@^x509_extensions\t=.*@x509_extensions\t= server_cert@" -i Intermediate/openssl.cnf sed -e "/^\[ $section \]$/,/^\[/ s@^#[ \t]*copy_extensions[ \t]*=.*@copy_extensions = copy@" -i Intermediate/openssl.cnf sed -e "/^\[ $section \]$/,/^\[/ s@^policy[ \t]*=.*@policy\t\t= policy_anything@" -i Intermediate/openssl.cnf # configure v2 certificate revocation list support sed -e "/^\[ $section \]$/,/^\[/ s@^#[ \t]*crl_extensions[ \t]*=.*@crl_extensions\t= crl_ext@" -i Intermediate/openssl.cnf - configure intermediate for signing server certificates:
cat >> Intermediate/openssl.cnf << EOF [ server_cert ] # Extensions for server certificates (man x509v3_config). basicConstraints = CA:FALSE nsCertType = server nsComment = 'OpenSSL Generated Server Certificate' subjectKeyIdentifier = hash authorityKeyIdentifier = keyid,issuer:always keyUsage = critical, nonRepudiation, digitalSignature, keyEncipherment extendedKeyUsage = serverAuth crlDistributionPoints = URI:http://example.net/intermediatecrl.pem EOF - generate private key:
openssl genpkey -aes256 -algorithm RSA -out Intermediate/private/intermediatekey.pem -pkeyopt rsa_keygen_bits:4096 - generate certificate signing request:
openssl req -config Intermediate/openssl.cnf -key Intermediate/private/intermediatekey.pem -new -out Intermediate/csr/intermediatecsr.pem -subj /C=CY/ST=ProvinceState/L=City/O=Organization/CN=intermediate-001.example.net - inspect the certificate signing request:
openssl req -in Intermediate/csr/intermediatecsr.pem -noout -text - sign intermediate certificate:
openssl ca -batch -config CA/openssl.cnf -extensions v3_intermediate_ca -notext -in Intermediate/csr/intermediatecsr.pem -out Intermediate/certs/intermediatecert.pem - inspect the intermediate certificate:
openssl x509 -dates -ext basicConstraints,crlDistributionPoints -in Intermediate/certs/intermediatecert.pem -issuer -noout -subject - verify the intermediate certificate:
openssl verify -CAfile CA/certs/cacert.pem Intermediate/certs/intermediatecert.pem - create certificate chain file:
cat Intermediate/certs/intermediatecert.pem CA/certs/cacert.pem > Intermediate/certs/ca-chaincert.pem
create server certificate
- copy and update the configuration file:
# prepare server directory mkdir -p Server/{certs,csr,private} chmod u=rwx,g=,o= Server/private # initialize files cp /etc/pki/tls/openssl.cnf Server/ # prepare configuration file sed -e "/^\[ req \]$/,/^\[/ s@^attributes[ \t]*=.*@# &@" -i Server/openssl.cnf - generate private key:
openssl genpkey -algorithm RSA -out Server/private/serverkey.pem -pkeyopt rsa_keygen_bits:2048 - generate certificate signing request:
openssl req -addext 'subjectAltName = DNS:example.net,DNS:www.example.net,DNS:m.example.net' -config Server/openssl.cnf -key Server/private/serverkey.pem -new -out Server/csr/servercsr.pem -subj /CN=www.example.net - inspect the certificate signing request:
openssl req -in Server/csr/servercsr.pem -noout -text - sign server certificate:
openssl ca -batch -config Intermediate/openssl.cnf -extensions server_cert -notext -in Server/csr/servercsr.pem -out Server/certs/servercert.pem - inspect the server certificate:
openssl x509 -dates -ext basicConstraints,crlDistributionPoints -in Server/certs/servercert.pem -issuer -noout -subject - verify the server certificate:
openssl verify -CAfile Intermediate/certs/ca-chaincert.pem Server/certs/servercert.pem
operate
root (certificate authority)
- revoke intermediate certificate:
openssl ca -config CA/openssl.cnf -revoke Intermediate/certs/intermediatecert.pem - publish certificate status:
- generate the CRL:
openssl ca -config CA/openssl.cnf -gencrl -out CA/crl/cacrl.pem - inspect the CRL:
openssl crl -CAfile CA/certs/cacert.pem -in CA/crl/cacrl.pem -noout -text - verify the CRL:
openssl crl -CAfile CA/certs/cacert.pem -in CA/crl/cacrl.pem -noout -verify - host
CA/crl/cacrl.pemat the crlDistributionPoints URI configured inCA/openssl.cnf
- generate the CRL:
intermediate
- revoke server certificate:
openssl ca -config Intermediate/openssl.cnf -revoke Server/certs/servercert.pem - publish certificate status:
- generate the CRL:
openssl ca -config Intermediate/openssl.cnf -gencrl -out Intermediate/crl/intermediatecrl.pem - inspect the CRL:
openssl crl -CAfile Intermediate/certs/intermediatecert.pem -in Intermediate/crl/intermediatecrl.pem -noout -text - verify the CRL:
openssl crl -CAfile Intermediate/certs/intermediatecert.pem -in Intermediate/crl/intermediatecrl.pem -noout -verify - host
Intermediate/crl/intermediatecrl.pemat the crlDistributionPoints URI configured inIntermediate/openssl.cnf
- generate the CRL:
secure
- consider offline root CA
- consider frequent CRL updates to obviate the need for OCSP
Public and private keys
- Public key certificate
- commands:
openssl genpkey: generates private key or parametersopenssl list -public-key-algorithms: lists supported algorithmsopenssl pkeyparam: prints and validates parametersopenssl pkeyutl: performs low level public key operations (sign data, recover signed data, verify signature, derive shared secret)
parameter generation:
- valid algorithms: DH, DSA and EC
- examples:
openssl genpkey -genparam -algorithm DH -out dh-params.pem -outform PEM -pkeyopt dh_paramgen_prime_len:2048openssl genpkey -genparam -algorithm DSA -out dsa-params.pem -outform PEM -pkeyopt dsa_paramgen_bits:2048openssl genpkey -genparam -algorithm EC -out ec-params.pem -outform PEM -pkeyopt ec_paramgen_curve:P-256
parameter validation:
- examples:
openssl pkeyparam -check -in dh-params.pem -textopenssl pkeyparam -check -in dsa-params.pem -nooutopenssl pkeyparam -in ec-params.pem -text