Shopify/statsd-instrument — pull request #28 by kpumuk (2013-10-03 16:24:21+00:00)
Title: Optimized UDPSocket send to use cached resolved address

In Ruby every when UDPSocket#send called with host and port, address is being resolved and packed, which leads to several system calls, transferring about 12kb of data. There is an option to pre-pack address once, and then use this packed value for sending messages. Benchmark shows up to 6x speed improvement when using IP addresses, and up to 50-100x with DNS names.

Benchmarking code:

require 'benchmark'
require 'socket'

COUNT = 10000
addr = Socket.pack_sockaddr_in(3434, '127.0.0.1')
localhost_addr = Socket.pack_sockaddr_in(3434, 'localhost')
remote_addr = Socket.pack_sockaddr_in(3434, 'graphite.local')
sock = UDPSocket.new
Benchmark.bm(20) do |b|
b.report("plain") { COUNT.times { sock.send('test', 0, '127.0.0.1', 3434) } }
b.report("plain localhost") { COUNT.times { sock.send('test', 0, 'localhost', 3434) } }
b.report("plain remote") { COUNT.times { sock.send('test', 0, 'graphite.local', 3434) } }
b.report("optimized") { COUNT.times { sock.send('test', 0, addr) } }
b.report("optimized localhost") { COUNT.times { sock.send('test', 0, localhost_addr) } }
b.report("optimized remote") { COUNT.times { sock.send('test', 0, remote_addr) } }
end

Benchmark results:

user system total real
plain 0.050000 0.230000 0.280000 ( 0.279888)
plain localhost 0.130000 0.400000 0.530000 ( 0.530194)
plain remote 0.290000 0.690000 0.980000 ( 3.562078)
optimized 0.010000 0.060000 0.070000 ( 0.070118)
optimized localhost 0.000000 0.060000 0.060000 ( 0.069770)
optimized remote 0.010000 0.030000 0.040000 ( 0.028374)