Diferencia entre revisiones de «Crear un CA para firmar certificados SSL»
Sin resumen de edición |
|||
| Línea 51: | Línea 51: | ||
Firmar la solicitud de certificado con la CA | Firmar la solicitud de certificado con la CA | ||
openssl ca -config openssl.conf -extensions v3_req -days 3650 -notext -md sha256 -in csr/${DOMINIO}.csr.pem -out certs/${DOMINIO}.cert.pem | openssl ca -config openssl.conf -policy policy_loose -extensions v3_req -days 3650 -notext -md sha256 -in csr/${DOMINIO}.csr.pem -out certs/${DOMINIO}.cert.pem | ||
chmod 444 certs/${DOMINIO}.cert.pem | chmod 444 certs/${DOMINIO}.cert.pem | ||
Revisión actual - 11:16 4 feb 2022
Problema: estamos practicando SSL/TLS y queremos ir más allá de los certificados auto-firmados. Además es un incordio estar añadiendo las excepciones de seguridad en los programas cliente, y además quiero usar comodines en los dominios.
Solución: crear una clave privada+certificado de una CA, usarla para firmar certificados, e importar esa CA a Firefox y Thunderbird para que confien en ella.
Procedimiento
Practicamente todo está tomado de este fantástico artículo Crear autoridad certificadora (CA) y certificados autofirmados en Linux. ¡Muchas gracias Antonio Guillen!
Basicamente lo que ves aquí es una simplificación de ese artículo.
Creamos un directorio vacío como base, aquí va a estar la CA.
export BASE='/root/ca' mkdir $BASE cd $BASE
mkdir certs csr crl newcerts private chmod 700 private touch index.txt touch index.txt.attr echo 1000 > serial
Creamos el fichero openssl.conf, puedes ver el contenido al final.
Creamos la clave privada de la CA
openssl genrsa -aes256 -out ./private/ca.key.pem 4096 chmod 400 ./private/ca.key.pem
Generamos el certificado de la CA (En Common Name ponemos lo que queramos)
URL=luisantolin.com export SAN=DNS:$URL openssl req -config openssl.conf -key private/ca.key.pem -new -x509 -days 7300 -sha256 -extensions v3_ca -out certs/ca.cert.pem chmod 444 certs/ca.cert.pem
Crear una clave privada para nuestro sitio web.
URL="*.miweb.com"
DOMINIO=$(echo $URL | sed 's/*\.//g' )
openssl genrsa -out ./private/${DOMINIO}.key.pem 2048
chmod 400 ./private/${DOMINIO}.key.pem
Generar la solicitud de certificado (en Common Name ponemos el DOMINIO)
URL="*.miweb.com"
DOMINIO=$(echo $URL | sed 's/*\.//g' )
export SAN=DNS:$URL,DNS:$DOMINIO
openssl req -config openssl.conf -key private/${DOMINIO}.key.pem -new -sha256 -out csr/${DOMINIO}.csr.pem
Firmar la solicitud de certificado con la CA
openssl ca -config openssl.conf -policy policy_loose -extensions v3_req -days 3650 -notext -md sha256 -in csr/${DOMINIO}.csr.pem -out certs/${DOMINIO}.cert.pem
chmod 444 certs/${DOMINIO}.cert.pem
Convertimos el certificado en DER, por si nos lo piden en ese formato, tenerlo ya
openssl x509 -in certs/${DOMINIO}.cert.pem -out certs/${DOMINIO}.cert.der -outform DER
Ahora hay colocar el certs/DOMINIO.cert.pem y el private/DOMINIO.key.pem al servidor (Apache, o Postfix, o Dovecot), en donde corresponda en cada caso.
Por ultimo hay que importar el certs/ca.cert.pem en los clientes. En Mar-2021, para Firefox Linux y para Thunderbird Linux, en Ubuntu 20.04 LTS el procedimiento es trivial, basta con ir a opciones, buscar certificados, ahi CAs e importar el PEM.
openssl.conf
[ ca ]
# man ca
default_ca = CA_default
[ CA_default ]
# Directory and file locations.
dir = ./
certs = ./certs
crl_dir = ./crl
new_certs_dir = ./newcerts
database = ./index.txt
serial = ./serial
RANDFILE = ./private/.rand
# The root key and root certificate.
private_key = ./private/ca.key.pem
certificate = ./certs/ca.cert.pem
# For certificate revocation lists.
crlnumber = ./crlnumber
crl = ./crl/ca.crl.pem
crl_extensions = crl_ext
default_crl_days = 30
# SHA-1 is deprecated, so use SHA-2 instead.
default_md = sha256
name_opt = ca_default
cert_opt = ca_default
default_days = 375
preserve = no
policy = policy_strict
[ policy_strict ]
# The root CA should only sign intermediate certificates that match.
# See the POLICY FORMAT section of man ca.
countryName = match
stateOrProvinceName = match
organizationName = match
organizationalUnitName = optional
commonName = supplied
emailAddress = optional
[ policy_loose ]
# Allow the intermediate CA to sign a more diverse range of certificates.
# See the POLICY FORMAT section of the ca man page.
countryName = optional
stateOrProvinceName = optional
localityName = optional
organizationName = optional
organizationalUnitName = optional
commonName = supplied
emailAddress = optional
[ req ]
# Options for the req tool (man req).
default_bits = 2048
distinguished_name = req_distinguished_name
string_mask = utf8only
# SHA-1 is deprecated, so use SHA-2 instead.
default_md = sha256
# Extension to add when the -x509 option is used.
x509_extensions = v3_ca
# Extension for SANs
req_extensions = v3_req
[ v3_req ]
# Extensions to add to a certificate request
# Before invoke openssl use: export SAN=DNS:value1,DNS:value2
basicConstraints = CA:FALSE
keyUsage = nonRepudiation, digitalSignature, keyEncipherment
subjectAltName = ${ENV::SAN}
[ req_distinguished_name ]
# See <https://en.wikipedia.org/wiki/Certificate_signing_request>.
countryName = Country Name (2 letter code)
stateOrProvinceName = State or Province Name
localityName = Locality Name
0.organizationName = Organization Name
organizationalUnitName = Organizational Unit Name
commonName = Common Name
emailAddress = Email Address
# Optionally, specify some defaults.
countryName_default = CO
stateOrProvinceName_default = Coruscant
localityName_default = Ciudad Galactica
0.organizationName_default = Consejo Jedi
organizationalUnitName_default = CJ
emailAddress_default = consejo@templo.jedi.org
[ v3_ca ]
# Extensions for a typical CA (man x509v3_config).
subjectKeyIdentifier = hash
authorityKeyIdentifier = keyid:always,issuer
basicConstraints = critical, CA:true
keyUsage = critical, digitalSignature, cRLSign, keyCertSign
[ v3_intermediate_ca ]
# Extensions for a typical intermediate CA (man x509v3_config).
subjectKeyIdentifier = hash
authorityKeyIdentifier = keyid:always,issuer
basicConstraints = critical, CA:true, pathlen:0
keyUsage = critical, digitalSignature, cRLSign, keyCertSign
[ usr_cert ]
# Extensions for client certificates (man x509v3_config).
basicConstraints = CA:FALSE
nsCertType = client, email
nsComment = "OpenSSL Generated Client Certificate"
subjectKeyIdentifier = hash
authorityKeyIdentifier = keyid,issuer
keyUsage = critical, nonRepudiation, digitalSignature, keyEncipherment
extendedKeyUsage = clientAuth, emailProtection
[ 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, digitalSignature, keyEncipherment
extendedKeyUsage = serverAuth
[ crl_ext ]
# Extension for CRLs (man x509v3_config).
authorityKeyIdentifier=keyid:always
[ ocsp ]
# Extension for OCSP signing certificates (man ocsp).
basicConstraints = CA:FALSE
subjectKeyIdentifier = hash
authorityKeyIdentifier = keyid,issuer
keyUsage = critical, digitalSignature
extendedKeyUsage = critical, OCSPSigning