Convert RSA to OPENSSH - bash

I will preface this that I am extremely inexperienced with certs/keys and I am using a Mac.
My problem is with RSA and OPENSSH certs/keys. I currently have a valid RSA cert/key, but I need to convert them to OpenSSH. From my understanding, I want to do the opposite of this thread: Openssh Private Key to RSA Private Key
I have a file that starts with:
-----BEGIN RSA PRIVATE KEY-----
But I need to convert it to this:
-----BEGIN OPENSSH PRIVATE KEY-----
I have tried ssh-keygen -p -N "" -m pem -f /path/to/key and ssh-keygen -f /path/to/key -m pem but it does not output with the OPENSSH header I expected.
Is this possible?
If it is possible, what can I use to perform this conversion and what would a potential command be?
Do I need to do anything to convert the cert if I converted the key?
If I do need to convert the cert, what is the command for that?
If there is any further explanation on what converting from RSA to OPENSSH is, I would really appreciate it.

As long as you are using -m PEM in your command, the result won't be an OPENSSH format.
This will convert an RSA/PEM private key into an OPENSSH one:
ssh-keygen -p -N "" -f /path/to/key
You can then extract its public key and confirm it is identical to the one you have before:
ssh-keygen -y -f /path/to/key

Related

How to get the fingerprint of an encrypted ssh private key in go?

Is there a way to get the fingerprint of a passphrase protected ssh private key in go without knowing the passphrase?
I know it's possible using the openssh tools:
$ ssh-keygen -t rsa -b 4096 -f identity -N passphrase
# ...
$ ssh-keygen -l -f identity.pub
4096 SHA256:ecFemcAlOhQyFk/HWfAnx14T+SGuQImMvmEt+T1DarM x#x (RSA)
$ ssh-keygen -l -f identity
4096 SHA256:ecFemcAlOhQyFk/HWfAnx14T+SGuQImMvmEt+T1DarM x#x (RSA)
In go (golang.org/x/crypto/ssh) the ssh.ParsePrivateKey(key) returns a PassPhraseMissingError and a nil key, so I can't call ssh.FingerprintSHA256(key.PublicKey()) on it.
I would like to do this because then I could check if the agent can handle that key so that I don't need to let it try every key known by the agent when connecting.

Redis Public Keys

I am working on HackTheBox and have come across a question that Google has yet to answer. The current script looks like so:
#!/bin/bash
rm /root/.ssh/id*
ssh-keygen -t rsa
(echo -e "\n\n";cat "/root/.ssh/id_rsa.pub";echo -e "\n\n") > "/root/Desktop/postmanKey.txt"
redis-cli -h 10.10.10.160 flushall
cat "/root/Desktop/postmanKey.txt" | redis-cli -h 10.10.10.160 -x set bb
redis-cli -h 10.10.10.160 save
redis-cli -h 10.10.10.160 set dbfilename "authorized_keys"
redis-cli -h 10.10.10.160 save
ssh -i "/root/.ssh/id_rsa" redis#10.10.10.160
I understand all of it except for one thing. Why do we do (echo -e "\n\n";cat "/root/.ssh/id_rsa.pub";echo -e "\n\n") > "/root/Desktop/postmanKey.txt" to generate a public key with 2 trailing and 2 following newlines? I have done some tinkering and quite a few Google searches but I have yet to turn up the reason why this is necessary. If I push the file to the server without the newlines and then attempt to connect via ssh, I am unable to. My only thought is maybe this is something to do with the common format of private keys:
-----BEGIN RSA PRIVATE KEY-----
....
-----END RSA PRIVATE KEY-----
however, we are connecting with a private key, but pushing to the server a public key... hence why I am lost. Thank you for any information!

What is the significance ot the makecert -sk keyname option?

I am using makecert.exe to create an RSA certificate and I am wondering what the significance is of this option? -sk KeyName
The documentation says "Specifies the subject's key container location, which contains the private key. If a key container does not exist, it will be created"
But I don't know what that means. Is it used as some kind of seed for creating the certificate? This is my current command line:
makecert.exe -r -sr LocalMachine -ss my -a sha256 -pe -sky exchange -n "CN=Mycert"
Under what circumstances might I want to specify a KeyName?

Unattended generation of an ECDSA key using gpg2

Short question
How do I specify an elliptic curve in a gpg2 v2.1.11 parameter file?
Long question
I have successfully used the following bash script to generate an RSA key using gpg2 v2.1.11:
#!/bin/bash
PUBRING_FILE=$(mktemp /tmp/pub.XXXXXX)
CONFIG_FILE=$(mktemp /tmp/config.XXXXXX)
cat >$CONFIG_FILE <<EOF
Key-Type: DSA
Key-Length: 1024
Subkey-Type: RSA
Subkey-Length: 2048
Name-Real: Name
Name-Comment: Comment
Name-Email: Email
Expire-Date: 0
Passphrase: abc
%pubring $PUBRING_FILE
EOF
gpg2 --quiet --batch --expert --full-gen-key $CONFIG_FILE
I want to use the same script to generate an ECDSA key. However, when I replace
Subkey-Type: RSA
Subkey-Length: 2048
with
Subkey-Type: ECDSA
Subkey-Length: 256
I get the following error
gpg: key generation failed: Unknown elliptic curve
My configuration file clearly omits the curve, but how can I include it? I.e., how do I specify an elliptic curve in a gpg2 v2.1.11 parameter file?
gpg2 does not know which EC curve you want to use. To fix this, you need to use the Key-Curve option. In your example you should remove the Subkey-Length: 2048 line and add a new Subkey-Curve: [...] option.
Example using the NIST P-256 curve:
cat >$CONFIG_FILE <<EOF
Key-Type: DSA
Key-Length: 1024
Subkey-Type: ECDSA
Subkey-Curve: nistp256
Name-Real: Name
Name-Comment: Comment
Name-Email: Email
Expire-Date: 0
Passphrase: abc
%pubring $PUBRING_FILE
EOF

How to check a public RSA key file

Inside a shell script I want verify public RSA file.
All I want to do is that find a way to check this file is a genuine public key file, nothing else.
Can I ask experts here what are the ways I can verify this input file to check this is a genuine public key file , not a regular file.
I will be using this public key file in future to validate an incoming encrypt gzip file but that is out of scope for now.
All I want is validate input file to check its genuine RSA public key file not an ordinary file.please note that I do not have any other files with me (eg : private key) .
e.g.: if the file is ‘public.pem’ I just want check inside that it’s a genuine RSA public key file not just a file with texts or file is not corrupted .
I’m already checking that file is not zero sized and md5 .
other possible checks I found
check file got text ‘BEGIN PUBLIC KEY’ and ‘END PUBLIC KEY’
Also found this command in google , Is there a better way to do this using openssl
‘openssl rsa -noout -text -inform PEM -in pubkey.pem -pubin’
Thanks
It's possible to use any public key format parser, including openssl or even parse key yourself as the format is not that difficult.
Command line tools set a non-zero exit code, when parsing fails:
openssl rsa -inform PEM -pubin -in pubkey.pem -noout &> /dev/null
if [ $? != 0 ] ; then
echo "this was definitely not a RSA public key in PEM format"
exit 1
fi
Just to check any public key:
openssl pkey -inform PEM -pubin -in pubkey.pem -noout &> /dev/null
if [ $? != 0 ] ; then
echo "this was definitely not a public key in PEM format"
exit 1
fi
The following script should work for all PEM-formatted keys and certs supported by OpenSSL. I have tested it on various valid and invalid ECDSA and RSA keys with matching and non-matching certs.
Save this as verify-cert-key:
#!/usr/bin/env bash
certFile="${1}"
keyFile="${2}"
certPubKey="$(openssl x509 -noout -pubkey -in "${certFile}")"
keyPubKey="$(openssl pkey -pubout -in "${keyFile}")"
if [[ "${certPubKey}" == "${keyPubKey}" ]]
then
echo "PASS: key and cert match"
else
echo "FAIL: key and cert DO NOT match"
fi
Make it executable:
chmod +x verify-cert-key
Run it on a cert and key:
./verify-cert-key server-crt.pem server-key.pem
Try this command if your public key starts with -----BEGIN RSA PUBLIC KEY-----
openssl rsa -RSAPublicKey_in -in /path/to/pub_key.pem -noout -text

Resources