class Rex::Proto::Kademlia::BootstrapResponse

A Kademlia bootstrap response message

Constants

BOOTSTRAP_PEER_SIZE

The minimum size of a peer in a KADEMLIA2_BOOTSTRAP_RES message: peer ID (16-bytes), IP (4 bytes), UDP port (2 bytes), TCP port (2 bytes) and version (1 byte)

Attributes

peer_id[R]

@return [String] the ID of the peer that send the bootstrap response

peers[R]

@return [Array<Hash<String, Object>>] the peer ID, IP address, UDP/TCP ports and version of each peer

tcp_port[R]

@return [Integer] the TCP port that the responding peer is listening on

version[R]

@return [Integer] the version of this peer

Public Class Methods

from_data(data) click to toggle source

Builds a bootstrap response from given data

@param data [String] the data to decode @return [BootstrapResponse] the bootstrap response if the data is valid, nil otherwise

# File lib/rex/proto/kademlia/bootstrap_response.rb, line 44
def self.from_data(data)
  message = Message.from_data(data)
  # abort if this isn't a valid response
  return unless message
  return unless message.type == BOOTSTRAP_RESPONSE
  return unless message.body.size >= 23
  bootstrap_peer_id = Rex::Proto::Kademlia.decode_peer_id(message.body.slice!(0, 16))
  bootstrap_tcp_port, bootstrap_version, num_peers = message.body.slice!(0, 5).unpack('vCv')
  # protocol says there are no peers and the body confirms this, so just return with no peers
  if num_peers == 0 && message.body.to_s.empty?
    peers = []
  else
    peers_data = message.body
    # peers data is too long/short, abort
    return if peers_data.size % BOOTSTRAP_PEER_SIZE != 0
    peers = []
    until peers_data.to_s.empty?
      peer_data = peers_data.slice!(0, BOOTSTRAP_PEER_SIZE)
      peer_id = Rex::Proto::Kademlia.decode_peer_id(peer_data.slice!(0, 16))
      ip, udp_port, tcp_port, version = peer_data.unpack('VvvC')
      peers << {
        id: peer_id,
        ip: Rex::Socket.addr_itoa(ip),
        tcp_port: tcp_port,
        udp_port: udp_port,
        version: version
      }
    end
  end
  BootstrapResponse.new(bootstrap_peer_id, bootstrap_tcp_port, bootstrap_version, peers)
end
new(peer_id, tcp_port, version, peers) click to toggle source

Constructs a new bootstrap response

@param peer_id [String] the ID of this peer @param tcp_port [Integer] the TCP port that this peer is listening on @param version [Integer] the version of this peer @param peers [Array<Hash<String, Object>>] the peer ID, IP address, UDP/TCP ports and version of each peer

# File lib/rex/proto/kademlia/bootstrap_response.rb, line 28
def initialize(peer_id, tcp_port, version, peers)
  @peer_id = peer_id
  @tcp_port = tcp_port
  @version = version
  @peers = peers
end