Skip to content

Commit

Permalink
Added ssh-ed25519 to HostKeys algorithms
Browse files Browse the repository at this point in the history
  • Loading branch information
mfazekas committed Dec 11, 2016
1 parent 13a963a commit 3622f63
Show file tree
Hide file tree
Showing 10 changed files with 77 additions and 21 deletions.
4 changes: 4 additions & 0 deletions CHANGES.txt
Original file line number Diff line number Diff line change
@@ -1,3 +1,7 @@
=== 4.0.0.rc2

* Added ssh-ed25519 to KnownHosts:SUPPORTED_TYPE [detatka-kuzlatka-otevrete, Miklós Fazekas, #459]

=== 4.0.0.rc1

* Allow :password to be nil for capistrano v2 compatibility [Will Bryant, #357]
Expand Down
7 changes: 4 additions & 3 deletions Gemfile
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ unless Gem.win_platform? || RUBY_PLATFORM == "java"
gem 'byebug', group: [:development, :test]
end

gem 'simplecov', require: false, group: :test

gem 'codecov', require: false, group: :test if ENV["CI"]
if ENV["CI"]
gem 'simplecov', require: false, group: :test
gem 'codecov', require: false, group: :test
end
4 changes: 2 additions & 2 deletions Gemfile.norbnacl
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ ENV['NET_SSH_NO_RBNACL'] = 'true'
# Specify your gem's dependencies in mygem.gemspec
gemspec

unless Gem.win_platform?
if ENV["CI"] && !Gem.win_platform?
gem 'simplecov', require: false, group: :test
gem 'codecov', require: false, group: :test if ENV["CI"]
gem 'codecov', require: false, group: :test
end
4 changes: 2 additions & 2 deletions Gemfile.norbnacl.lock
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
PATH
remote: .
specs:
net-ssh (4.0.0.beta3)
net-ssh (4.0.0.rc1)

GEM
remote: https://rubygems.org/
Expand Down Expand Up @@ -38,4 +38,4 @@ DEPENDENCIES
rubocop (~> 0.39.0)

BUNDLED WITH
1.13.5
1.13.6
7 changes: 2 additions & 5 deletions lib/net/ssh/key_factory.rb
Original file line number Diff line number Diff line change
Expand Up @@ -109,11 +109,8 @@ def load_data_public_key(data, filename="")
# appropriately.
def classify_key(data, filename)
if data.match(/-----BEGIN OPENSSH PRIVATE KEY-----/)
if defined?(Net::SSH::Authentication::ED25519)
return ->(key_data, passphrase) { Net::SSH::Authentication::ED25519::PrivKey.read(key_data, passphrase) }, [ArgumentError]
else
raise OpenSSL::PKey::PKeyError, "OpenSSH keys only supported if ED25519 is available - #{ED25519_LOAD_ERROR}"
end
Net::SSH::Authentication::ED25519Loader.raiseUnlessLoaded("OpenSSH keys only supported if ED25519 is available")
return ->(key_data, passphrase) { Net::SSH::Authentication::ED25519::PrivKey.read(key_data, passphrase) }, [ArgumentError]
elsif OpenSSL::PKey.respond_to?(:read)
return ->(key_data, passphrase) { OpenSSL::PKey.read(key_data, passphrase) }, [ArgumentError, OpenSSL::PKey::PKeyError]
elsif data.match(/-----BEGIN DSA PRIVATE KEY-----/)
Expand Down
6 changes: 5 additions & 1 deletion lib/net/ssh/transport/algorithms.rb
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
require 'net/ssh/transport/hmac'
require 'net/ssh/transport/kex'
require 'net/ssh/transport/server_version'
require 'net/ssh/authentication/ed25519_loader'

module Net; module SSH; module Transport

Expand Down Expand Up @@ -42,12 +43,15 @@ class Algorithms
hmac-sha2-512-96 none),

:compression => %w(none [email protected] zlib),
:language => %w()
:language => %w()
}
if defined?(OpenSSL::PKey::EC)
ALGORITHMS[:host_key] += %w(ecdsa-sha2-nistp256
ecdsa-sha2-nistp384
ecdsa-sha2-nistp521)
if Net::SSH::Authentication::ED25519Loader::LOADED
ALGORITHMS[:host_key] += %w(ssh-ed25519)
end
ALGORITHMS[:kex] += %w(ecdh-sha2-nistp256
ecdh-sha2-nistp384
ecdh-sha2-nistp521)
Expand Down
17 changes: 17 additions & 0 deletions test/integration/common.rb
Original file line number Diff line number Diff line change
Expand Up @@ -61,4 +61,21 @@ def ssh_add(key,password)
raise "Command: #{command} failed:#{status.exitstatus}" unless status
status.exitstatus
end

def with_sshd_config(sshd_config, &block)
raise "Failed to copy config" unless system("sudo cp -f /etc/ssh/sshd_config /etc/ssh/sshd_config.original")
begin
Tempfile.open('sshd_config') do |f|
f.write(sshd_config)
f.close
system("sudo cp -f #{f.path} /etc/ssh/sshd_config")
end
system("sudo chmod 0644 /etc/ssh/sshd_config")
raise "Failed to restart sshd" unless system("sudo service ssh restart")
yield
ensure
system("sudo cp -f /etc/ssh/sshd_config.original /etc/ssh/sshd_config")
system("sudo service ssh restart")
end
end
end
23 changes: 22 additions & 1 deletion test/integration/test_ed25519_pkeys.rb
Original file line number Diff line number Diff line change
Expand Up @@ -68,6 +68,27 @@ def test_in_file_with_password
assert_equal "hello from:net_ssh_1\n", ret
end
end

def test_with_only_ed25519_host_key
config_lines = File.read('/etc/ssh/sshd_config').split("\n")
config_lines = config_lines.map do |line|
if (line =~ /^HostKey /) && !(line =~ /ed25519/)
"##{line}"
else
line
end
end

Tempfile.open('empty_kh') do |f|
f.close
with_sshd_config(config_lines.join("\n")) do
ret = Net::SSH.start("localhost", "net_ssh_1", password: 'foopwd', user_known_hosts_file: [f.path]) do |ssh|
ssh.exec! "echo 'foo'"
end
assert_equal "foo\n", ret
end
end
end
end

end
end
24 changes: 18 additions & 6 deletions test/transport/test_algorithms.rb
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@ def test_allowed_packets
end

def test_constructor_should_build_default_list_of_preferred_algorithms
assert_equal %w(ssh-rsa ssh-dss [email protected] [email protected])+ec_host_keys, algorithms[:host_key]
assert_equal %w(ssh-rsa ssh-dss [email protected] [email protected])+ec_ed_host_keys, algorithms[:host_key]
assert_equal %w(diffie-hellman-group-exchange-sha1 diffie-hellman-group1-sha1 diffie-hellman-group14-sha1 diffie-hellman-group-exchange-sha256)+ec_kex, algorithms[:kex]
assert_equal %w(aes128-cbc 3des-cbc blowfish-cbc cast128-cbc aes192-cbc aes256-cbc [email protected] idea-cbc none arcfour128 arcfour256 arcfour aes128-ctr aes192-ctr aes256-ctr cast128-ctr blowfish-ctr 3des-ctr), algorithms[:encryption]
if defined?(OpenSSL::Digest::SHA256)
Expand All @@ -36,12 +36,20 @@ def test_constructor_should_set_client_and_server_prefs_identically
end

def test_constructor_with_preferred_host_key_type_should_put_preferred_host_key_type_first
assert_equal %w(ssh-dss ssh-rsa [email protected] [email protected])+ec_host_keys, algorithms(:host_key => "ssh-dss", :append_all_supported_algorithms => true)[:host_key]
assert_equal %w(ssh-dss ssh-rsa [email protected] [email protected])+ec_ed_host_keys, algorithms(:host_key => "ssh-dss", :append_all_supported_algorithms => true)[:host_key]
end

def test_constructor_with_known_hosts_reporting_known_host_key_should_use_that_host_key_type
Net::SSH::KnownHosts.expects(:search_for).with("net.ssh.test,127.0.0.1", {}).returns([stub("key", :ssh_type => "ssh-dss")])
assert_equal %w(ssh-dss ssh-rsa [email protected] [email protected] )+ec_host_keys, algorithms[:host_key]
assert_equal %w(ssh-dss ssh-rsa [email protected] [email protected] )+ec_ed_host_keys, algorithms[:host_key]
end

def ed_host_keys
if Net::SSH::Authentication::ED25519Loader::LOADED
%w(ssh-ed25519)
else
[]
end
end

def ec_host_keys
Expand All @@ -52,8 +60,12 @@ def ec_host_keys
end
end

def ec_ed_host_keys
ec_host_keys + ed_host_keys
end

def test_constructor_with_unrecognized_host_key_type_should_return_whats_supported
assert_equal %w(ssh-rsa ssh-dss [email protected] [email protected] )+ec_host_keys, algorithms(:host_key => "bogus ssh-rsa",:append_all_supported_algorithms => true)[:host_key]
assert_equal %w(ssh-rsa ssh-dss [email protected] [email protected] )+ec_ed_host_keys, algorithms(:host_key => "bogus ssh-rsa",:append_all_supported_algorithms => true)[:host_key]
end

def ec_kex
Expand Down Expand Up @@ -95,7 +107,7 @@ def test_constructor_with_multiple_preferred_hmac_should_put_all_preferred_hmac_
end

def test_constructor_with_unrecognized_hmac_should_ignore_those
assert_equal %w(hmac-md5-96 hmac-sha1 hmac-md5 hmac-sha1-96 hmac-ripemd160 [email protected] hmac-sha2-256 hmac-sha2-512 hmac-sha2-256-96 hmac-sha2-512-96 none),
assert_equal %w(hmac-md5-96 hmac-sha1 hmac-md5 hmac-sha1-96 hmac-ripemd160 [email protected] hmac-sha2-256 hmac-sha2-512 hmac-sha2-256-96 hmac-sha2-512-96 none),
algorithms(:hmac => "hmac-md5-96", :append_all_supported_algorithms => true)[:hmac]
end

Expand Down Expand Up @@ -294,7 +306,7 @@ def assert_kexinit(buffer, options={})
assert_equal KEXINIT, buffer.type
assert_equal 16, buffer.read(16).length
assert_equal options[:kex] || (%w(diffie-hellman-group-exchange-sha1 diffie-hellman-group1-sha1 diffie-hellman-group14-sha1 diffie-hellman-group-exchange-sha256)+ec_kex).join(','), buffer.read_string
assert_equal options[:host_key] || (%w(ssh-rsa ssh-dss [email protected] [email protected])+ec_host_keys).join(','), buffer.read_string
assert_equal options[:host_key] || (%w(ssh-rsa ssh-dss [email protected] [email protected])+ec_ed_host_keys).join(','), buffer.read_string
assert_equal options[:encryption_client] || "aes128-cbc,3des-cbc,blowfish-cbc,cast128-cbc,aes192-cbc,aes256-cbc,[email protected],idea-cbc,none,arcfour128,arcfour256,arcfour,aes128-ctr,aes192-ctr,aes256-ctr,cast128-ctr,blowfish-ctr,3des-ctr", buffer.read_string
assert_equal options[:encryption_server] || "aes128-cbc,3des-cbc,blowfish-cbc,cast128-cbc,aes192-cbc,aes256-cbc,[email protected],idea-cbc,none,arcfour128,arcfour256,arcfour,aes128-ctr,aes192-ctr,aes256-ctr,cast128-ctr,blowfish-ctr,3des-ctr", buffer.read_string
assert_equal options[:hmac_client] || "hmac-sha1,hmac-md5,hmac-sha1-96,hmac-md5-96,hmac-ripemd160,[email protected],hmac-sha2-256,hmac-sha2-512,hmac-sha2-256-96,hmac-sha2-512-96,none", buffer.read_string
Expand Down
2 changes: 1 addition & 1 deletion test/transport/test_session.rb
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
require 'common'
require_relative '../common'
require 'net/ssh/transport/session'

# mocha adds #verify to Object, which throws off the host-key-verifier part of
Expand Down

0 comments on commit 3622f63

Please sign in to comment.