Class UDPSocket
In: lib/resolv-replace.rb
ext/socket/socket.c
Parent: Object

Class Socket provides access to the underlying operating system socket implementations. It can be used to provide more operating system specific functionality than the protocol-specific socket classes but at the expense of greater complexity. In particular, the class handles addresses using +struct sockaddr+ structures packed into Ruby strings, which can be a joy to manipulate.

Exception Handling

Ruby‘s implementation of Socket causes an exception to be raised based on the error generated by the system dependent implementation. This is why the methods are documented in a way that isolate Unix-based system exceptions from Windows based exceptions. If more information on particular exception is needed please refer to the Unix manual pages or the Windows WinSock reference.

Documentation by

  • Zach Dennis
  • Sam Roberts
  • Programming Ruby from The Pragmatic Bookshelf.

Much material in this documentation is taken with permission from Programming Ruby from The Pragmatic Bookshelf.

Methods

External Aliases

bind -> original_resolv_bind
connect -> original_resolv_connect
send -> original_resolv_send

Public Instance methods

[Source]

    # File lib/resolv-replace.rb, line 25
25:   def bind(host, port)
26:     host = IPSocket.getaddress(host) if host != ""
27:     original_resolv_bind(host, port)
28:   end

[Source]

    # File lib/resolv-replace.rb, line 31
31:   def connect(host, port)
32:     original_resolv_connect(IPSocket.getaddress(host), port)
33:   end

Receives up to maxlen bytes from udpsocket using recvfrom(2) after O_NONBLOCK is set for the underlying file descriptor. flags is zero or more of the MSG_ options. The first element of the results, mesg, is the data received. The second element, sender_inet_addr, is an array to represent the sender address.

When recvfrom(2) returns 0, Socket#recvfrom_nonblock returns an empty string as data. It means an empty packet.

Parameters

  • maxlen - the number of bytes to receive from the socket
  • flags - zero or more of the MSG_ options

Example

     require 'socket'
     s1 = UDPSocket.new
     s1.bind("127.0.0.1", 0)
     s2 = UDPSocket.new
     s2.bind("127.0.0.1", 0)
     s2.connect(*s1.addr.values_at(3,1))
     s1.connect(*s2.addr.values_at(3,1))
     s1.send "aaa", 0
     IO.select([s2])
     p s2.recvfrom_nonblock(10)  #=> ["aaa", ["AF_INET", 33302, "localhost.localdomain", "127.0.0.1"]]

Refer to Socket#recvfrom for the exceptions that may be thrown if the call to recvfrom_nonblock fails.

UDPSocket#recvfrom_nonblock may raise any error corresponding to recvfrom(2) failure, including Errno::EAGAIN.

See

[Source]

/*
 * call-seq:
 *      udpsocket.recvfrom_nonblock(maxlen) => [mesg, sender_inet_addr]
 *      udpsocket.recvfrom_nonblock(maxlen, flags) => [mesg, sender_inet_addr]
 * 
 * Receives up to _maxlen_ bytes from +udpsocket+ using recvfrom(2) after
 * O_NONBLOCK is set for the underlying file descriptor.
 * _flags_ is zero or more of the +MSG_+ options.
 * The first element of the results, _mesg_, is the data received.
 * The second element, _sender_inet_addr_, is an array to represent the sender address.
 *
 * When recvfrom(2) returns 0,
 * Socket#recvfrom_nonblock returns an empty string as data.
 * It means an empty packet.
 * 
 * === Parameters
 * * +maxlen+ - the number of bytes to receive from the socket
 * * +flags+ - zero or more of the +MSG_+ options 
 * 
 * === Example
 *      require 'socket'
 *      s1 = UDPSocket.new
 *      s1.bind("127.0.0.1", 0)
 *      s2 = UDPSocket.new
 *      s2.bind("127.0.0.1", 0)
 *      s2.connect(*s1.addr.values_at(3,1))
 *      s1.connect(*s2.addr.values_at(3,1))
 *      s1.send "aaa", 0
 *      IO.select([s2])
 *      p s2.recvfrom_nonblock(10)  #=> ["aaa", ["AF_INET", 33302, "localhost.localdomain", "127.0.0.1"]]
 *
 * Refer to Socket#recvfrom for the exceptions that may be thrown if the call
 * to _recvfrom_nonblock_ fails. 
 *
 * UDPSocket#recvfrom_nonblock may raise any error corresponding to recvfrom(2) failure,
 * including Errno::EAGAIN.
 *
 * === See
 * * Socket#recvfrom
 */
static VALUE
udp_recvfrom_nonblock(int argc, VALUE *argv, VALUE sock)
{
    return s_recvfrom_nonblock(sock, argc, argv, RECV_IP);
}

[Source]

    # File lib/resolv-replace.rb, line 36
36:   def send(mesg, flags, *rest)
37:     if rest.length == 2
38:       host, port = rest
39:       begin
40:         addrs = Resolv.getaddresses(host)
41:       rescue Resolv::ResolvError
42:         raise SocketError, "Hostname not known: #{host}"
43:       end
44:       err = nil
45:       addrs[0...-1].each {|addr|
46:         begin
47:           return original_resolv_send(mesg, flags, addr, port)
48:         rescue SystemCallError
49:         end
50:       }
51:       original_resolv_send(mesg, flags, addrs[-1], port)
52:     else
53:       original_resolv_send(mesg, flags, *rest)
54:     end
55:   end

[Validate]