Reputation: 71
I'm trying to read in some public key files generated with:
for i in $(seq 1 100); do
ssh-keygen -t rsa -f keys/$i -q -N ""
done
I'm using ruby and my code is below. The problem I'm having is that I can't be sure I'm doing it correctly. I thought that the public key was a large number generated by multiplying 2 large prime numbers. I'm getting numbers that are divisible by 3, 15, 33, and/or some other numbers. These are all multiples of prime numbers but I was expecting only 2 prime numbers, not 3 or 4. It may be that I am using ruby incorrectly or that I am misunderstanding the format of a public key. Any help would be greatly appreciated.
#!/usr/bin/env ruby
pubhash = Hash.new
# Read in public key files
pubfiles = File.join("**", "*.pub")
Dir.glob(pubfiles) do |filename|
File.open(filename) do |file|
file.each do |line|
base64 = line.chomp.split[1]
bytes = base64.unpack("m").first.unpack("C*").reverse
key = bytes.each_with_index.inject(0) do
|sum, (byte, index)|
sum + byte * (256 ** index)
end
pubhash[filename] = key
end
file.close
end
end
EDIT solution thanks to the link that Charlie provided:
File.open(filename) do |file|
file.each do |line|
base64 = line.chomp.split[1]
keydata = base64.unpack("m").first
parts = Array.new
while (keydata.length > 0)
dlen = keydata[0, 4].bytes.inject(0) do |a, b|
(a << 8) + b
end
data = keydata[4, dlen]
keydata = keydata[(dlen + 4)..-1]
parts.push(data)
end
@type = parts[0]
@e = parts[1].bytes.inject do |a, b|
(a << 8) + b
end
@n = parts[2].bytes.inject do |a, b|
(a << 8) + b
end
end
file.close
end
Upvotes: 0
Views: 704
Reputation: 7349
The reason you're finding other divisors of this number is likely because the base64 block contains more than just the key.
For example, I used ssh-keygen -t rsa -b 768 -C so-is-cool
to generate a keypair and have this as my .pub:
ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAAAYQDK92Q/FMsaOuBE9NL7OufMYWVPWj62F6QXl4ADcYgFMrGMJRF1njg5UGujgqaIrouGjoqudt23fykUNG7HRZV4M4Plxknj4TSvFIG5hi+6x/AQzzPP7xnLkYBKDOxSs+M= so-is-cool
Fire up IRB:
base64='AAAAB3NzaC1yc2EAAAADAQABAAAAYQDK92Q/FMsaOuBE9NL7OufMYWVPWj62F6QXl4ADcYgFMrGMJRF1njg5UGujgqaIrouGjoqudt23fykUNG7HRZV4M4Plxknj4TSvFIG5hi+6x/AQzzPP7xnLkYBKDOxSs+M='
base64.unpack('m').first
You will see that the first bytes of it are:
\x00\x00\x00\assh-rsa\x00\x00\x00\
or in other words my key algorithm. You probably need to parse this value a bit more to be of actual value. I found this blog that discusses the format of the OpenSSH .pub file a bit: http://blog.oddbit.com/2011/05/08/converting-openssh-public-keys/
Upvotes: 1