class NetworkClipboard::Discovery

Attributes

receive_socket[R]

Public Class Methods

new(config) click to toggle source
# File lib/network_clipboard/discovery.rb, line 9
def initialize(config)
  @config = config

  @receive_socket = UDPSocket.new()
  @receive_socket.setsockopt(:IPPROTO_IP, :IP_ADD_MEMBERSHIP, multicast_addr.hton + bind_addr.hton)
  @receive_socket.bind(bind_addr.to_s,port)

  @send_socket = UDPSocket.new()
  @send_socket.setsockopt(:IPPROTO_IP, :IP_MULTICAST_TTL, 1)
  @send_socket.connect(multicast_addr.to_s,port)

  @authenticated_client_id = [
    @config.client_id,
    Digest::HMAC.digest(@config.secret,@config.client_id,Digest::SHA256),
  ].pack("H32A32")
end

Public Instance Methods

announce() click to toggle source
# File lib/network_clipboard/discovery.rb, line 38
def announce
  @send_socket.send(@authenticated_client_id,0)
end
bind_addr() click to toggle source
# File lib/network_clipboard/discovery.rb, line 30
def bind_addr
  @bind_addr ||= IPAddr.new('0.0.0.0')
end
get_peer_announcement() click to toggle source
# File lib/network_clipboard/discovery.rb, line 42
def get_peer_announcement
  while true
    msg,ip = @receive_socket.recvfrom(65536)
    other_client_id,other_digest = msg.unpack('H32A32')

    # Retry if we got our own announcement.
    next if other_client_id == @config.client_id

    # We could do a constant time string compare, but an attacker can
    # just listen to announces and rebroadcast them as his own anyway.
    # This is just to skip other honest clients with different secrets
    # on the network, to avoid wasting time on a failed handshake.
    next unless other_digest == Digest::HMAC.digest(@config.secret,other_client_id,Digest::SHA256)

    return [other_client_id,ip[2]]
  end
end
multicast_addr() click to toggle source
# File lib/network_clipboard/discovery.rb, line 34
def multicast_addr
  @multicast_addr ||= IPAddr.new(@config.multicast_ip)
end
port() click to toggle source
# File lib/network_clipboard/discovery.rb, line 26
def port
  @port ||= @config.port
end