开发者

Use RSA private key to generate public key? [closed]

Closed. This question does not meet Stack Overflow guidelines. It is not currently accepting answers.

This question does not appear to be about a specific programming problem, a software algorithm, or software tools primarily used by programmers. If you believe the question would be on-topic on another Stack Exchange site, you can leave a comment to explain where the question may be able to be answered.

Closed 9 months ago.

The community reviewed whether to reopen this question 9 months ago and left it closed:

Original close reason(s) were not resolved

开发者_StackOverflow
Improve this question

I don't really understand this one:

According to https://www.madboa.com/geek/openssl/#key-rsa, you can generate a public key from a private key.

openssl genrsa -out mykey.pem 1024
openssl rsa -in mykey.pem -pubout > mykey.pub

My initial thinking was that they are generated in a pair together.

Does the RSA private key contain the sum? Or the public key?


openssl genrsa -out mykey.pem 1024

will actually produce a public - private key pair. The pair is stored in the generated mykey.pem file.

openssl rsa -in mykey.pem -pubout > mykey.pub

will extract the public key and print that out. Here is a link to a page that describes this better.

EDIT: Check the examples section here. To just output the public part of a private key:

openssl rsa -in key.pem -pubout -out pubkey.pem

To get a usable public key for SSH purposes, use ssh-keygen:

ssh-keygen -y -f key.pem > key.pub


People looking for SSH public key...

If you're looking to extract the public key for use with OpenSSH, you will need to get the public key a bit differently

$ ssh-keygen -y -f mykey.pem > mykey.pub

This public key format is compatible with OpenSSH. Append the public key to remote:~/.ssh/authorized_keys and you'll be good to go


docs from SSH-KEYGEN(1)

ssh-keygen -y [-f input_keyfile]  

-y This option will read a private OpenSSH format file and print an OpenSSH public key to stdout.


In most software that generates RSA private keys, including OpenSSL's, the private key is represented as a PKCS#1 RSAPrivatekey object or some variant thereof:

A.1.2 RSA private key syntax

An RSA private key should be represented with the ASN.1 type
RSAPrivateKey:

  RSAPrivateKey ::= SEQUENCE {
      version           Version,
      modulus           INTEGER,  -- n
      publicExponent    INTEGER,  -- e
      privateExponent   INTEGER,  -- d
      prime1            INTEGER,  -- p
      prime2            INTEGER,  -- q
      exponent1         INTEGER,  -- d mod (p-1)
      exponent2         INTEGER,  -- d mod (q-1)
      coefficient       INTEGER,  -- (inverse of q) mod p
      otherPrimeInfos   OtherPrimeInfos OPTIONAL
  }

As you can see, this format has a number of fields including the modulus and public exponent and thus is a strict superset of the information in an RSA public key.


My answer below is a bit lengthy, but hopefully it provides some details that are missing in previous answers. I'll start with some related statements and finally answer the initial question.

To encrypt something using RSA algorithm you need modulus and encryption (public) exponent pair (n, e). That's your public key. To decrypt something using RSA algorithm you need modulus and decryption (private) exponent pair (n, d). That's your private key.

To encrypt something using RSA public key you treat your plaintext as a number and raise it to the power of e modulus n:

ciphertext = ( plaintext^e ) mod n

To decrypt something using RSA private key you treat your ciphertext as a number and raise it to the power of d modulus n:

plaintext = ( ciphertext^d ) mod n

To generate private (d,n) key using openssl you can use the following command:

openssl genrsa -out private.pem 1024

To generate public (e,n) key from the private key using openssl you can use the following command:

openssl rsa -in private.pem -out public.pem -pubout

To dissect the contents of the private.pem private RSA key generated by the openssl command above run the following (output truncated to labels here):

openssl rsa -in private.pem -text -noout | less

modulus         - n
privateExponent - d
publicExponent  - e
prime1          - p
prime2          - q
exponent1       - d mod (p-1)
exponent2       - d mod (q-1)
coefficient     - (q^-1) mod p

Shouldn't private key consist of (n, d) pair only? Why are there 6 extra components? It contains e (public exponent) so that public RSA key can be generated/extracted/derived from the private.pem private RSA key. The rest 5 components are there to speed up the decryption process. It turns out that by pre-computing and storing those 5 values it is possible to speed the RSA decryption by the factor of 4. Decryption will work without those 5 components, but it can be done faster if you have them handy. The speeding up algorithm is based on the Chinese Remainder Theorem.

Yes, private.pem RSA private key actually contains all of those 8 values; none of them are generated on the fly when you run the previous command. Try running the following commands and compare output:

# Convert the key from PEM to DER (binary) format
openssl rsa -in private.pem -outform der -out private.der

# Print private.der private key contents as binary stream
xxd -p private.der

# Now compare the output of the above command with output 
# of the earlier openssl command that outputs private key
# components. If you stare at both outputs long enough
# you should be able to confirm that all components are
# indeed lurking somewhere in the binary stream
openssl rsa -in private.pem -text -noout | less

This structure of the RSA private key is recommended by the PKCS#1 v1.5 as an alternative (second) representation. PKCS#1 v2.0 standard excludes e and d exponents from the alternative representation altogether. PKCS#1 v2.1 and v2.2 propose further changes to the alternative representation, by optionally including more CRT-related components.

To see the contents of the public.pem public RSA key run the following (output truncated to labels here):

openssl rsa -in public.pem -text -pubin -noout

Modulus             - n
Exponent (public)   - e

No surprises here. It's just (n, e) pair, as promised.

Now finally answering the initial question: As was shown above private RSA key generated using openssl contains components of both public and private keys and some more. When you generate/extract/derive public key from the private key, openssl copies two of those components (e,n) into a separate file which becomes your public key.


The Public Key is not stored in the PEM file as some people think. The following DER structure is present on the Private Key File:

openssl rsa -text -in mykey.pem

RSAPrivateKey ::= SEQUENCE {
  version           Version,
  modulus           INTEGER,  -- n
  publicExponent    INTEGER,  -- e
  privateExponent   INTEGER,  -- d
  prime1            INTEGER,  -- p
  prime2            INTEGER,  -- q
  exponent1         INTEGER,  -- d mod (p-1)
  exponent2         INTEGER,  -- d mod (q-1)
  coefficient       INTEGER,  -- (inverse of q) mod p
  otherPrimeInfos   OtherPrimeInfos OPTIONAL
}

So there is enough data to calculate the Public Key (modulus and public exponent), which is what openssl rsa -in mykey.pem -pubout does


here in this code first we are creating RSA key which is private but it has pair of its public key as well so to get your actual public key we simply do this

openssl rsa -in mykey.pem -pubout > mykey.pub

hope you get it for more info check this


Firstly a quick recap on RSA key generation.

  1. Randomly pick two random probable primes of the appropriate size (p and q).
  2. Multiply the two primes together to produce the modulus (n).
  3. Pick a public exponent (e).
  4. Do some math with the primes and the public exponent to produce the private exponent (d).

The public key consists of the modulus and the public exponent.

A minimal private key would consist of the modulus and the private exponent. There is no computationally feasible surefire way to go from a known modulus and private exponent to the corresponding public exponent.

However:

  1. Practical private key formats nearly always store more than n and d.
  2. e is normally not picked randomly, one of a handful of well-known values is used. If e is one of the well-known values and you know d then it would be easy to figure out e by trial and error.

So in most practical RSA implementations you can get the public key from the private key. It would be possible to build a RSA based cryptosystem where this was not possible, but it is not the done thing.


The file called "private key" includes much more information than the private key alone, it includes all the data (primes, modulus, exponents, etc..) needed to generate private/public key pair.

And it is very easy to see see this information:

openssl genrsa -out private.pem 1024   #generate private key file
openssl rsa -in private.pem -text      #view info in the private key file
openssl rsa -in private.pem -pubout -out public.pem  #extract public key to file
openssl rsa -in public.pem -pubin -text  #view info in the public key file

You will see that that private key file includes the primes with all other information while the public file includes only the modulus and the public exponent.


Seems to be a common feature of the prevalent asymmetric cryptography; the generation of public/private keys involves generating the private key, which contains the key pair:

openssl genrsa -out mykey.pem 1024

Then publish the public key:

openssl rsa -in mykey.pem -pubout > mykey.pub

or

openssl rsa -in mykey.pem -pubout -out mykey.pub

DSA & EC crypto keys have same feature: eg.

openssl genpkey -algorithm ed25519 -out pvt.pem

Then

openssl pkey -in pvt.pem -pubout > public.pem

or

openssl ec -in ecprivkey.pem -pubout -out ecpubkey.pem

The public component is involved in decryption, and keeping it as part of the private key makes decryption faster; it can be removed from the private key and calculated when needed (for decryption), as an alternative or complement to encrypting or protecting the private key with a password/key/phrase. eg.

openssl pkey -in key.pem -des3 -out keyout.pem

or

openssl ec -aes-128-cbc -in pk8file.pem -out tradfile.pem

You can replace the first argument "aes-128-cbc" with any other valid openssl cipher name


Use the following commands:

  1. openssl req -x509 -nodes -days 365 -sha256 -newkey rsa:2048 -keyout mycert.pem -out mycert.pem

     Loading 'screen' into random state - done
     Generating a 2048 bit RSA private key
     .............+++
     ..................................................................................................................................................................+++
     writing new private key to 'mycert.pem'
     -----
     You are about to be asked to enter information that will be incorporated
     into your certificate request.
     What you are about to enter is what is called a Distinguished Name or a DN.
     There are quite a few fields but you can leave some blank
     For some fields there will be a default value,
     If you enter '.', the field will be left blank.
    
  2. If you check there will be a file created by the name : mycert.pem

  3. openssl rsa -in mycert.pem -pubout > mykey.txt

    writing RSA key
    
  4. If you check the same file location a new public key mykey.txt has been created.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜