26

Similar to how it can be easily done for RSA:

openssl req -x509 -nodes -newkey rsa:2048 -rand /dev/urandom -keyout example.key -out example.crt -days 365

I'd like to generate an ECDSA cert/key in one step. I've tried:

openssl req -x509 -nodes -newkey ec:secp384r1 -keyout ecdsa.pem -out mycert.crt -days 30

Returns the below error

Can't open parameter file secp384r1.

I am trying to specify the curve to use. If a key file exists, then you can specify it with ec:example-ecdsa.pem and it will work.

Possibly something like this could work with tweaking:

openssl req -new -x509 -nodes -newkey ec:$(openssl ecparam -name secp384r1) -keyout cert.key -out cert.crt -days 3650
Python Novice
  • 531
  • 1
  • 6
  • 11
  • Why would you use `/dev/urandom`? If you care about safety, use `/dev/random/`, which has much higher entropy. `/dev/random` will always wait until it has good entropy, while `/dev/urandom` is unblocking. – Diti May 19 '14 at 09:19
  • 7
    @Diti: sorry, you got it completely in reverse. `/dev/random` is NOT "safer" than `/dev/urandom`; in fact, it is rather the opposite, precisely since `/dev/random` blocks. See: http://www.2uo.de/myths-about-urandom/ – Tom Leek Jun 17 '14 at 10:47
  • 1
    @Tom: Don't feel sorry for pointing that mistake out, I actually appreciated that; your link was a great read! Thank you! I should be careful when giving cryptography advise, haha! – Diti Jun 17 '14 at 13:14

4 Answers4

28

This seemed to be the command you want:

openssl req -new -x509 -nodes -newkey ec:<(openssl ecparam -name secp384r1) -keyout cert.key -out cert.crt -days 3650
user23013
  • 660
  • 5
  • 11
  • It calls openssl twice. Not that it is a problem in itself, but when running openssl from windows this solution does not work. That's why i'd reccomend the solution posted by @Jude – Andre Soares Feb 26 '20 at 20:08
  • 1
    Nice solution. As an additional information -- in case you would want to create an Ed25519 key, you go with this one liner: openssl req -new -x509 -nodes -newkey ed25519 -keyout cert.key -out cert.crt -days 3650 – Pawel Os. Nov 02 '21 at 09:13
20

Use -pkeyopt

openssl req -x509 -nodes -newkey ec -pkeyopt ec_paramgen_curve:secp384r1 -keyout ecdsa.pem -out mycert.crt -days 30

According to man req:

OPTIONS
       -pkeyopt opt:value
           set the public key algorithm option opt to value. The precise set of options supported depends on the public key algorithm used and its implementation. See KEY GENERATION OPTIONS in the genpkey manual page for more details.

So then looking at man genpkey:

EC PARAMETER GENERATION OPTIONS
       The EC parameter generation options below can also be supplied as EC key generation options. This can (for example) generate a key from a named curve without the need to use an explicit parameter file.

       ec_paramgen_curve:curve
           the EC curve to use. OpenSSL supports NIST curve names such as "P-256".

       ec_param_enc:encoding
           the encoding to use for parameters. The "encoding" parameter must be either "named_curve" or "explicit".
Jude
  • 301
  • 2
  • 3
  • 1
    This is the only answer that really calls openssl just once – Andre Soares Feb 26 '20 at 20:06
  • and the only one that can be run from a cloud-init script where the input redirection in the other example freaks out – grenade Apr 22 '21 at 07:50
  • A note here: This seems to need a bit more modern OpenSSL. It does not work with LibreSSL 2.8.3 and I also think it does not work with OpenSSL 1.0.2. However this method also works fine on windows since it does not use unix shell specific redirection. – plaisthos Jul 29 '21 at 11:30
  • @plaisthos I'm using `OpenSSL 1.0.2k-fips 26 Jan 2017` on RHEL 7 and it's working for me. – miken32 Aug 20 '22 at 16:46
  • @plaisthos+ for me in 1.0.2 it produces a key&cert -- but with explicit encoding, which violates 5480 and things like SSL/TLS can't use, so I must add `-pkeyopt ec_param_enc:named_curve` to make it usable. For 1.1.0 up, named is the default. (Below 1.0.2 the options are invalid.) – dave_thompson_085 Aug 21 '22 at 01:19
6
openssl ecparam -name secp521r1 -genkey -param_enc explicit -out private-key.pem
openssl req -new -x509 -key private-key.pem -out server.pem -days 730

Creating Self-Signed ECDSA SSL Certificate using OpenSSL is working for me.

You can test certificates after generating as follows.

openssl ecparam -in private-key.pem -text -noout
Kasun
  • 784
  • 2
  • 5
  • 13
  • 2
    I am well aware of that. My question specifically asked how it can be done in one step. – Python Novice May 18 '14 at 02:31
  • command1 && command2 will work as single line executing two commands. Even that $(command) is close to that. In that you are fetching out of one command to other. – Kasun May 18 '14 at 08:04
  • 1
    @Kasun The poster was asking how to call openssl once, creating the keypair and cert at the same time, using the ec:filename option. – mikemaccana Jul 11 '16 at 10:26
1

To create ECC secp384r1 key + CSR with Alternative Subject Names:

fqdn="www.example.com"
fqdna="DNS.1=$fqdn, DNS.2=example.com, DNS.3=es.example.com, DNS.4=it.example.com, DNS.5=pt.example.com, DNS.6=de.example.com, DNS.7=fr.example.com"
subject="/C=US/ST=Minnesota/L=Minneapolis/O=Me and my Feast/OU=IT Dept./CN=$fqdn/subjectAltName=$fqdna"

openssl req -new -nodes -keyout $fqdn.secp384r1.key \
  -newkey ec:<(openssl ecparam -name secp384r1 -rand /dev/urandom) \
  -out $fqdn.secp384r1.csr -subj $subject
miken32
  • 103
  • 4