-
Notifications
You must be signed in to change notification settings - Fork 5.4k
/
Copy pathbind_spec.rb
150 lines (120 loc) · 4.33 KB
/
bind_spec.rb
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
require_relative '../spec_helper'
require_relative '../fixtures/classes'
describe "Socket#bind on SOCK_DGRAM socket" do
before :each do
@sock = Socket.new(Socket::AF_INET, Socket::SOCK_DGRAM, 0)
@sockaddr = Socket.pack_sockaddr_in(0, "127.0.0.1")
end
after :each do
@sock.closed?.should be_false
@sock.close
end
it "binds to a port" do
-> { @sock.bind(@sockaddr) }.should_not raise_error
end
it "returns 0 if successful" do
@sock.bind(@sockaddr).should == 0
end
it "raises Errno::EINVAL when already bound" do
@sock.bind(@sockaddr)
-> { @sock.bind(@sockaddr) }.should raise_error(Errno::EINVAL)
end
it "raises Errno::EADDRNOTAVAIL when the specified sockaddr is not available from the local machine" do
sockaddr1 = Socket.pack_sockaddr_in(0, "4.3.2.1")
-> { @sock.bind(sockaddr1) }.should raise_error(Errno::EADDRNOTAVAIL)
end
platform_is_not :windows, :cygwin do
as_user do
break if File.read('/proc/sys/net/ipv4/ip_unprivileged_port_start').to_i <= 1 rescue nil
it "raises Errno::EACCES when the current user does not have permission to bind" do
sockaddr1 = Socket.pack_sockaddr_in(1, "127.0.0.1")
-> { @sock.bind(sockaddr1) }.should raise_error(Errno::EACCES)
end
end
end
end
describe "Socket#bind on SOCK_STREAM socket" do
before :each do
@sock = Socket.new(Socket::AF_INET, Socket::SOCK_STREAM, 0)
@sock.setsockopt(Socket::SOL_SOCKET, Socket::SO_REUSEADDR, true)
@sockaddr = Socket.pack_sockaddr_in(0, "127.0.0.1")
end
after :each do
@sock.closed?.should be_false
@sock.close
end
it "binds to a port" do
-> { @sock.bind(@sockaddr) }.should_not raise_error
end
it "returns 0 if successful" do
@sock.bind(@sockaddr).should == 0
end
it "raises Errno::EINVAL when already bound" do
@sock.bind(@sockaddr)
-> { @sock.bind(@sockaddr) }.should raise_error(Errno::EINVAL)
end
it "raises Errno::EADDRNOTAVAIL when the specified sockaddr is not available from the local machine" do
sockaddr1 = Socket.pack_sockaddr_in(0, "4.3.2.1")
-> { @sock.bind(sockaddr1) }.should raise_error(Errno::EADDRNOTAVAIL)
end
platform_is_not :windows, :cygwin do
as_user do
break if File.read('/proc/sys/net/ipv4/ip_unprivileged_port_start').to_i <= 1 rescue nil
it "raises Errno::EACCES when the current user does not have permission to bind" do
sockaddr1 = Socket.pack_sockaddr_in(1, "127.0.0.1")
-> { @sock.bind(sockaddr1) }.should raise_error(Errno::EACCES)
end
end
end
end
describe 'Socket#bind' do
SocketSpecs.each_ip_protocol do |family, ip_address|
describe 'using a packed socket address' do
before do
@socket = Socket.new(family, :DGRAM)
@sockaddr = Socket.sockaddr_in(0, ip_address)
end
after do
@socket.close
end
it 'returns 0 when successfully bound' do
@socket.bind(@sockaddr).should == 0
end
it 'raises Errno::EINVAL when binding to an already bound port' do
@socket.bind(@sockaddr)
-> { @socket.bind(@sockaddr) }.should raise_error(Errno::EINVAL)
end
it 'raises Errno::EADDRNOTAVAIL when the specified sockaddr is not available' do
ip = family == Socket::AF_INET ? '4.3.2.1' : '::2'
sockaddr1 = Socket.sockaddr_in(0, ip)
-> { @socket.bind(sockaddr1) }.should raise_error(Errno::EADDRNOTAVAIL)
end
platform_is_not :windows do
as_user do
break if File.read('/proc/sys/net/ipv4/ip_unprivileged_port_start').to_i <= 1 rescue nil
it 'raises Errno::EACCES when the user is not allowed to bind to the port' do
sockaddr1 = Socket.pack_sockaddr_in(1, ip_address)
-> { @socket.bind(sockaddr1) }.should raise_error(Errno::EACCES)
end
end
end
end
describe 'using an Addrinfo' do
before do
@addr = Addrinfo.udp(ip_address, 0)
@socket = Socket.new(@addr.afamily, @addr.socktype)
end
after do
@socket.close
end
it 'binds to an Addrinfo' do
@socket.bind(@addr).should == 0
@socket.local_address.should be_an_instance_of(Addrinfo)
end
it 'uses a new Addrinfo for the local address' do
@socket.bind(@addr)
@socket.local_address.should_not == @addr
end
end
end
end