Socket.gethostbyname #2125

Closed
wants to merge 6 commits into
from
View
@@ -610,7 +610,23 @@ def self.gethostbyname(hostname)
alternatives = []
addrinfos.each do |a|
alternatives << a[2] unless a[2] == hostname
- addresses << a[3] if a[4] == family
+ # transform addresses to packed strings
+ if a[4] == family
+ sockaddr = Socket.sockaddr_in(1, a[3])
+ if family == AF_INET
+ # IPv4 address
+ offset = FFI.config("sockaddr_in.sin_addr.offset")
+ size = FFI.config("sockaddr_in.sin_addr.size")
+ addresses << sockaddr.byteslice(offset, size)
+ elsif family == AF_INET6
+ # Ipv6 address
+ offset = FFI.config("sockaddr_in6.sin6_addr.offset")
+ size = FFI.config("sockaddr_in6.sin6_addr.size")
+ addresses << sockaddr.byteslice(offset, size)
+ else
+ addresses << a[3]
+ end
+ end
end
[hostname, alternatives.uniq, family] + addresses.uniq
View
@@ -687,7 +687,23 @@ def self.gethostbyname(hostname)
alternatives = []
addrinfos.each do |a|
alternatives << a[2] unless a[2] == hostname
- addresses << a[3] if a[4] == family
+ # transform addresses to packed strings
+ if a[4] == family
+ sockaddr = Socket.sockaddr_in(1, a[3])
+ if family == AF_INET
+ # IPv4 address
+ offset = FFI.config("sockaddr_in.sin_addr.offset")
+ size = FFI.config("sockaddr_in.sin_addr.size")
+ addresses << sockaddr.byteslice(offset, size)
+ elsif family == AF_INET6
+ # Ipv6 address
+ offset = FFI.config("sockaddr_in6.sin6_addr.offset")
+ size = FFI.config("sockaddr_in6.sin6_addr.size")
+ addresses << sockaddr.byteslice(offset, size)
+ else
+ addresses << a[3]
+ end
+ end
end
[hostname, alternatives.uniq, family] + addresses.uniq
View
@@ -687,7 +687,23 @@ def self.gethostbyname(hostname)
alternatives = []
addrinfos.each do |a|
alternatives << a[2] unless a[2] == hostname
- addresses << a[3] if a[4] == family
+ # transform addresses to packed strings
+ if a[4] == family
+ sockaddr = Socket.sockaddr_in(1, a[3])
+ if family == AF_INET
+ # IPv4 address
+ offset = FFI.config("sockaddr_in.sin_addr.offset")
+ size = FFI.config("sockaddr_in.sin_addr.size")
+ addresses << sockaddr.byteslice(offset, size)
+ elsif family == AF_INET6
+ # Ipv6 address
+ offset = FFI.config("sockaddr_in6.sin6_addr.offset")
+ size = FFI.config("sockaddr_in6.sin6_addr.size")
+ addresses << sockaddr.byteslice(offset, size)
+ else
+ addresses << a[3]
+ end
+ end
end
[hostname, alternatives.uniq, family] + addresses.uniq
View
@@ -58,6 +58,23 @@ file 'runtime/platform.conf' => deps do |task|
s.field :sin_zero, :char_array
end.write_config(f)
+ Rubinius::FFI::Generators::Structures.new 'sockaddr_in6' do |s|
+ if BUILD_CONFIG[:windows]
+ s.include "ws2tcpip.h"
+ else
+ s.include "netinet/in.h"
+ s.include "sys/socket.h"
+ end
+ s.include "fcntl.h"
+ s.include "sys/stat.h"
+ s.name 'struct sockaddr_in6'
+ s.field :sin6_family, :sa_family_t
+ s.field :sin6_port, :ushort
+ s.field :sin6_flowinfo
+ s.field :sin6_addr, :char_array
+ s.field :sin6_scope_id
+ end.write_config(f)
+
unless BUILD_CONFIG[:windows]
sockaddr_un = Rubinius::FFI::Generators::Structures.new 'sockaddr_un' do |s|
s.include "sys/un.h"
@@ -13,4 +13,14 @@
addr = Socket.gethostbyname('<any>').first;
addr.should == "0.0.0.0"
end
+
+ it "returns address list in pack format (IPv4)" do
+ laddr = Socket.gethostbyname('127.0.0.1')[3..-1];
+ laddr.should == ["\x7f\x00\x00\x01"]
+ end
+
+ it "returns address list in pack format (IPv6)" do
+ laddr = Socket.gethostbyname('::1')[3..-1]
+ laddr.should == ["\x00" * 15 + "\x01"]
+ end
end