File: diffie_hellman_group_exchange_sha1.rb

package info (click to toggle)
ruby-net-ssh 1%3A6.1.0-2%2Bdeb11u1
  • links: PTS, VCS
  • area: main
  • in suites: bullseye
  • size: 1,884 kB
  • sloc: ruby: 15,997; makefile: 4
file content (73 lines) | stat: -rw-r--r-- 2,433 bytes parent folder | download
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
require 'net/ssh/errors'
require 'net/ssh/transport/constants'
require 'net/ssh/transport/kex/diffie_hellman_group1_sha1'

module Net::SSH::Transport::Kex
  # A key-exchange service implementing the
  # "diffie-hellman-group-exchange-sha1" key-exchange algorithm.
  class DiffieHellmanGroupExchangeSHA1 < DiffieHellmanGroup1SHA1
    MINIMUM_BITS      = 1024
    MAXIMUM_BITS      = 8192

    private

    # Compute the number of bits needed for the given number of bytes.
    def compute_need_bits
      # for Compatibility: OpenSSH requires (need_bits * 2 + 1) length of parameter
      need_bits = data[:need_bytes] * 8 * 2 + 1

      data[:minimum_dh_bits] ||= MINIMUM_BITS

      if need_bits < data[:minimum_dh_bits]
        need_bits = data[:minimum_dh_bits]
      elsif need_bits > MAXIMUM_BITS
        need_bits = MAXIMUM_BITS
      end

      data[:need_bits] = need_bits
      data[:need_bytes] = need_bits / 8
    end

    # Returns the DH key parameters for the given session.
    def get_parameters
      compute_need_bits

      # request the DH key parameters for the given number of bits.
      buffer = Net::SSH::Buffer.from(:byte, KEXDH_GEX_REQUEST, :long, data[:minimum_dh_bits],
        :long, data[:need_bits], :long, MAXIMUM_BITS)
      connection.send_message(buffer)

      buffer = connection.next_message
      raise Net::SSH::Exception, "expected KEXDH_GEX_GROUP, got #{buffer.type}" unless buffer.type == KEXDH_GEX_GROUP

      p = buffer.read_bignum
      g = buffer.read_bignum

      [p, g]
    end

    # Returns the INIT/REPLY constants used by this algorithm.
    def get_message_types
      [KEXDH_GEX_INIT, KEXDH_GEX_REPLY]
    end

    # Build the signature buffer to use when verifying a signature from
    # the server.
    def build_signature_buffer(result)
      response = Net::SSH::Buffer.new
      response.write_string data[:client_version_string],
                            data[:server_version_string],
                            data[:client_algorithm_packet],
                            data[:server_algorithm_packet],
                            result[:key_blob]
      response.write_long MINIMUM_BITS,
                          data[:need_bits],
                          MAXIMUM_BITS
      response.write_bignum dh.p, dh.g, dh.pub_key,
                            result[:server_dh_pubkey],
                            result[:shared_secret]
      response
    end
  end

end