Tech Blog.

Thoughts, stories, ideas.

OpenSSL x509 Zertifikate erstellen

29. June 2017

Es gibt (immer) noch diverse Server im Internet, die keine oder nur eine unzureichende SSL/TLS Konfiguration haben. Es handelt sich dabei nicht nur um Webserver (wie nginx oder Apache), sondern auch z.B. um XMPP/Jabber Server und Mailserver. Als Grundlage jeder SSL/TLS Konfiguration werden Keys und Zertifikate sowie allfällig auch noch Diffie-Hellman-Parameter benötigt. Dieser Artikel soll die wichtigsten Kommandos von OpenSSL zusammenfassen und kurz erklären.

Keys und Zertifikate erstellen

Um private Schlüssel und Zertifikate von Hand zu erstellen, kommen nachfolgend diverse nützliche Kommandos und deren Erklärungen.

Formate

Es gibt verschiedene Formate, wie Zertifikate und Keys gespeichert werden können. Nachfolgend wird immer das PEM-Format genutzt, dieses wird von den meisten Tools am besten unterstützt, die Dateien sind jedoch grösser als z.B. das DER-Format, da PEM aus ASCII Zeichen besteht und DER binär ist. Typische Endungen für PEM Zertifikate sind .pem oder .crt. Zertifikate im DER-Format sollten jeweils die Endung .der haben.

Das PEM-Format ist einfach zu erkennen, da der Inhalt der Dateien mit -----BEGIN CERTIFICATE----- anfängt und mit -----END CERTIFICATE----- endet. Ein guter Überblick der Formate und deren Umwandlung in jeweils andere Formate ist auf ssl.com erklärt.

Eine Liste der gängigsten Formate ist folgende:

  • PEM: Endung .pem, .crt, .cer
  • DER: Endung .der
  • PKCS#7: Endung .p7b, .p7c
  • PKCS#12: Endung .p12
  • PFX: Endung .pfx

Certificate Signing Request erstellen

Certificate Signing Requests (CSR) sind Anträge für neue Zertifikate. Diese müssen anschliessend entweder von einer Certificate Authority (CA) oder Self-Signed unterschrieben werden. Damit ein CSR erstellt werden kann, braucht es zuerst einen privaten Schlüssel. Normalerweise muss jedes mal wenn ein Zertifikat beantragt wird, ein neuer Certificate Signing Request erstellt werden.

Im ersten Schritt wird ein RSA Key mit 4096 Bit erstellt. Dies kann nach heutigen Standards als sicher angeschaut werden. Im zweiten Schritt wird der CSR erstellt, welcher mit SHA256 signiert wird (viele default Werte sind noch SHA1, deshalb sollte zwingend SHA256 explizit angegeben werden). Weitere Informationen zum Erstellen von RSA Keys kann in der Manpage von genrsa bzw. req für Certificate Signing Requests nachgelesen werden.

$ openssl genrsa -out example.com.key 4096
$ openssl req -new -sha256 -key example.com.key -out example.com.csr

Dies ist auch in einem Schritt möglich. Hier wird direkt ein CSR erstellt und dazu OpenSSL noch aufgefordert, den entsprechenden privaten Schlüssel zu erstellen.

$ openssl req -new -sha256 -nodes -newkey rsa:4096 -keyout example.com.key -out example.com.csr

Self-signed Certificate erstellen

Um schnell SSL Konfigurationen zu testen oder auf Servern, auf welchen nie geprüft wird, ob ein Zertifikat auch korrekt von einer Certificate Authority signiert wurde, können self-signed Zertifikate verwendet werden. Diese zu erstellen ist mit folgendem Kommando möglich. Es erstellt einen privaten Schlüssel, generiert daraus eine Certificate Signing Request und signiert diese mit dem privaten Schlüssel. Daraus folgt das Zertifikat, welches in example.com.pem abgelegt wird.

$ openssl req -x509 -sha256 -nodes -newkey rsa:4096 -keyout example.com.key -days 730 -out example.com.pem

Eigene CA erstellen und damit die Zertifikate signieren

Normale Zertifikate sollten die Berechtigung zum Signieren anderer Zertifikate nicht haben, dafür sollten spezielle Zertifikate zum Einsatz kommen, sogenannte Certificate Authorities (CA).

Ist die Anzahl der Clients überschaubar oder in anderen speziellen Fällen, kann eine eigene Certificate Authority (CA) erstellt werden. Dies ist zum Beispiel bei vielen Virtual Private Networks (VPN) nötig, da dort das Zertifikat des Servers und aller Clients signiert werden müssen.

Zuerst erstellen wir eine Datei (Dateiname z.B. x509.ext), in welcher die x509 Extensions definiert sind. Es gibt dafür zwei Abschnitte, den für die CA und den für Server Zertifikate.

[ ca ]
# X509 extensions for a ca
keyUsage                = critical, cRLSign, keyCertSign
basicConstraints        = CA:TRUE, pathlen:0
subjectKeyIdentifier    = hash
authorityKeyIdentifier  = keyid:always,issuer:always

[ server ]
# X509 extensions for a server
keyUsage                = critical,digitalSignature,keyEncipherment
extendedKeyUsage        = serverAuth,clientAuth
basicConstraints        = critical,CA:FALSE
subjectKeyIdentifier    = hash
authorityKeyIdentifier  = keyid,issuer:always

Danach erstellen wir die CA und die Server Zertifikate.

Im ersten Schritt wird ein neuer privater Schlüssel und ein Zertifikat erstellt, welches danach als Certificate Authority dient. Das Zertifikat der Certificate Authority hat in diesem Beispiel ein Ablaufdatum von 3 Jahren. Dieses Zertifikat darf nur zum Signieren weiterer Zertifikate genutzt werden (dies ist im Extension File im Abschnitt ca definiert).

Im zweiten Schritt wird das Server Zertifikat erstellt und von der CA signiert. Dem Zertifikat des Servers wird ein Ablaufdatum von 2 Jahren gesetzt. Weiter wird ein CA serial number File erstellt, wenn es nicht schon vorhanden ist. Dieses wird von der CA benötigt, damit die CA die aktuelle Seriennummer kennt. Das Server Zertifikat wird beim Signieren darauf eingeschränkt, dass es nur als Server oder Client agieren und keine weiteren Zertifikate signieren darf. Weitere Informationen sind in der Manpage von x509 und x509v3_config enthalten.

$ openssl req -new -sha256 -nodes -newkey rsa:4096 -keyout CA.key -out CA.csr
$ openssl x509 -req -sha256 -extfile x509.ext -extensions ca -in CA.csr -signkey CA.key -days 1095 -out CA.pem
$ openssl req -new -sha256 -nodes -newkey rsa:4096 -keyout www.example.com.key -out www.example.com.csr
$ openssl x509 -req -sha256 -CA CA.pem -CAkey CA.key -days 730 -CAcreateserial -CAserial CA.srl -extfile x509.ext -extensions server -in www.example.com.csr -out www.example.com.pem

Certificate und Certificate Signing Requests betrachten

Der Inhalt von Zertifikaten und Certificate Signing Requests kann am besten mit OpenSSL dargestellt werden. Nebst dem gesamten Inhalt (Option -text) können auch nur Teile davon dargestellt werden, so kann zum Beispiel das Erstell- und Ablaufdatum mit -dates dargestellt werden. Die entsprechende Liste ist in der Manpage (man 1 x509) unter dem Punkt Display options zu finden.

  • Certificate
$ openssl x509 -in example.com.pem -noout -text
  • Certificate Signing Request
$ openssl req -in example.com.csr -noout -text

Diffie-Hellman Parameter erstellen

Diffie-Hellman Parameter werden für Forward-Secrecy benötigt. Folgendes Kommando erstellt Diffie-Hellman Parameter mit 4096 Bit. Es ist nicht nötig so grosse Parameter zu erstellen, 2048 sollten auch reichen. Das Erstellen kann je nach Maschine extrem lange dauern. Es kann sich evtl. lohnen diese auf einer Hardware Maschine zu erstellen (da mehr Entropie vorhanden ist) und danach auf die virtuelle Maschine zu transferieren.

$ openssl dhparam -out dh4096.pem 4096

Konvertieren

Zertifikate können mit OpenSSL in andere Formate umgewandelt werden. Teilweise ist ein Zwischenschritt notwendig. Die gängigsten Umwandlungen, von DER zu PEM und umgekehrt, kann mit folgenden Kommandos gemacht werden:

$ openssl x509 -in cert.pem -outform der -out cert.der

und

$ openssl x509 -in cert.der -inform der -outform pem -out cert.pem

Das PKCS#12 und PFX Format kann mit folgenden Kommandos umgewandelt werden.

PFX (privater Schlüssel und Zertifikat) nach PEM (privater Schlüssel und Zertifikat):

$ openssl pkcs12 -in keyStore.pfx -out keyStore.pem -nodes

PEM (privater Schlüssel und Zertifikat) nach PFX (privater Schlüssel und Zertifikat):

$ openssl pkcs12 -export -out certificate.pfx -inkey privateKey.key -in certificate.crt -certfile CACert.crt

Weitere Kommandos zur Umwandlung finden sich auf bereits oben erwähnter Seite (ssl.com).