girl 9.1.2 → 9.1.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/lib/girl/dns.rb +52 -55
- data/lib/girl/head.rb +3 -4
- data/lib/girl/proxy.rb +61 -98
- data/lib/girl/proxy_worker.rb +1012 -1193
- data/lib/girl/proxyd.rb +52 -79
- data/lib/girl/proxyd_worker.rb +937 -709
- data/lib/girl/version.rb +1 -1
- metadata +3 -6
data/lib/girl/proxy_worker.rb
CHANGED
|
@@ -6,12 +6,11 @@ module Girl
|
|
|
6
6
|
redir_host,
|
|
7
7
|
redir_port,
|
|
8
8
|
memd_port,
|
|
9
|
-
relayd_host,
|
|
10
|
-
relayd_port,
|
|
11
9
|
tspd_host,
|
|
12
10
|
tspd_port,
|
|
13
11
|
proxyd_host,
|
|
14
12
|
proxyd_port,
|
|
13
|
+
bigd_port,
|
|
15
14
|
nameservers,
|
|
16
15
|
im,
|
|
17
16
|
directs,
|
|
@@ -26,18 +25,10 @@ module Girl
|
|
|
26
25
|
h_p1_close,
|
|
27
26
|
h_p2_close,
|
|
28
27
|
h_p2_traffic,
|
|
29
|
-
h_p1_overflow,
|
|
30
|
-
h_p1_underhalf,
|
|
31
|
-
h_p2_overflow,
|
|
32
|
-
h_p2_underhalf,
|
|
33
28
|
h_query,
|
|
34
29
|
h_response,
|
|
35
30
|
h_src_close,
|
|
36
31
|
h_traffic,
|
|
37
|
-
h_src_overflow,
|
|
38
|
-
h_src_underhalf,
|
|
39
|
-
h_dst_overflow,
|
|
40
|
-
h_dst_underhalf,
|
|
41
32
|
expire_connecting,
|
|
42
33
|
expire_long_after,
|
|
43
34
|
expire_proxy_after,
|
|
@@ -45,37 +36,37 @@ module Girl
|
|
|
45
36
|
expire_short_after,
|
|
46
37
|
is_debug,
|
|
47
38
|
is_client_fastopen,
|
|
48
|
-
is_server_fastopen
|
|
39
|
+
is_server_fastopen)
|
|
49
40
|
|
|
50
41
|
@proxyd_host = proxyd_host
|
|
51
|
-
@proxyd_addr = Socket.sockaddr_in(
|
|
52
|
-
@
|
|
42
|
+
@proxyd_addr = Socket.sockaddr_in(proxyd_port, proxyd_host)
|
|
43
|
+
@bigd_addr = Socket.sockaddr_in(bigd_port, proxyd_host)
|
|
44
|
+
@nameserver_addrs = nameservers.map{|n| Socket.sockaddr_in(53, n)}
|
|
53
45
|
@im = im
|
|
54
46
|
@directs = directs
|
|
55
47
|
@remotes = remotes
|
|
56
|
-
@local_ips = Socket.ip_address_list.select{
|
|
57
|
-
@update_roles = [
|
|
58
|
-
@updates_limit =
|
|
48
|
+
@local_ips = Socket.ip_address_list.select{|info| info.ipv4?}.map{|info| info.ip_address}
|
|
49
|
+
@update_roles = [:dns, :dst, :mem, :p1, :src, :rsv] # 参与淘汰的角色
|
|
50
|
+
@updates_limit = 1008 # 淘汰池上限,1015(mac) - info, infod, memd, proxy, redir, rsvd, tspd
|
|
59
51
|
@eliminate_count = 0 # 淘汰次数
|
|
60
52
|
@reads = [] # 读池
|
|
61
53
|
@writes = [] # 写池
|
|
62
|
-
@roles = {} # sock => :
|
|
54
|
+
@roles = {} # sock => :big / :dns / :dst / :infod / :mem / :memd / :p1 / :proxy / :redir / :rsv / :rsvd / :src / :tspd
|
|
63
55
|
@updates = {} # sock => updated_at
|
|
64
|
-
@proxy_infos = {} # proxy => {
|
|
65
|
-
@
|
|
66
|
-
@
|
|
67
|
-
@
|
|
68
|
-
@
|
|
69
|
-
@
|
|
70
|
-
@
|
|
71
|
-
@
|
|
72
|
-
@
|
|
73
|
-
@resolv_caches = {} # domain => [ ip, created_at ]
|
|
56
|
+
@proxy_infos = {} # proxy => {:is_syn :rbuff :recv_at :wbuff}
|
|
57
|
+
@big_infos = {} # big => {:is_syn :overflowing :rbuff :recv_at :wbuff}
|
|
58
|
+
@mem_infos = {} # mem => {:wbuff}
|
|
59
|
+
@src_infos = {} # src => {:addrinfo :closing :destination_domain :destination_port :dst :in :is_big :is_connect :overflowing :proxy_proto :proxy_type :rbuff :src_id :wbuff}
|
|
60
|
+
@dst_infos = {} # dst => {:closing :connected :domain :ip :overflowing :port :src :wbuff}
|
|
61
|
+
@dns_infos = {} # dns => {:domain :src}
|
|
62
|
+
@rsv_infos = {} # rsv => {:addrinfo :domain :type}
|
|
63
|
+
@near_infos = {} # near_id => {:addrinfo :created_at :domain :id :type}
|
|
64
|
+
@resolv_caches = {} # domain => [ip, created_at]
|
|
74
65
|
@is_direct_caches = {} # ip => true / false
|
|
75
|
-
@response_caches = {} # domain => [
|
|
76
|
-
@response6_caches = {} # domain => [
|
|
77
|
-
@p1_infos = {} # p1 => {
|
|
78
|
-
@appd_addr = Socket.sockaddr_in(
|
|
66
|
+
@response_caches = {} # domain => [response, created_at, ip, is_remote]
|
|
67
|
+
@response6_caches = {} # domain => [response, created_at, ip, is_remote]
|
|
68
|
+
@p1_infos = {} # p1 => {:closing :connected :in :is_big :overflowing :p2_id :wbuff}
|
|
69
|
+
@appd_addr = Socket.sockaddr_in(appd_port, appd_host)
|
|
79
70
|
|
|
80
71
|
@head_len = head_len
|
|
81
72
|
@h_a_new_source = h_a_new_source
|
|
@@ -85,18 +76,10 @@ module Girl
|
|
|
85
76
|
@h_p1_close = h_p1_close
|
|
86
77
|
@h_p2_close = h_p2_close
|
|
87
78
|
@h_p2_traffic = h_p2_traffic
|
|
88
|
-
@h_p1_overflow = h_p1_overflow
|
|
89
|
-
@h_p1_underhalf = h_p1_underhalf
|
|
90
|
-
@h_p2_overflow = h_p2_overflow
|
|
91
|
-
@h_p2_underhalf = h_p2_underhalf
|
|
92
79
|
@h_query = h_query
|
|
93
80
|
@h_response = h_response
|
|
94
81
|
@h_src_close = h_src_close
|
|
95
82
|
@h_traffic = h_traffic
|
|
96
|
-
@h_src_overflow = h_src_overflow
|
|
97
|
-
@h_src_underhalf = h_src_underhalf
|
|
98
|
-
@h_dst_overflow = h_dst_overflow
|
|
99
|
-
@h_dst_underhalf = h_dst_underhalf
|
|
100
83
|
@expire_connecting = expire_connecting
|
|
101
84
|
@expire_long_after = expire_long_after
|
|
102
85
|
@expire_proxy_after = expire_proxy_after
|
|
@@ -106,13 +89,13 @@ module Girl
|
|
|
106
89
|
@is_client_fastopen = is_client_fastopen
|
|
107
90
|
@is_server_fastopen = is_server_fastopen
|
|
108
91
|
|
|
109
|
-
new_a_redir(
|
|
110
|
-
new_a_infod(
|
|
111
|
-
new_a_memd(
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
new_a_tspd( tspd_host, tspd_port )
|
|
92
|
+
new_a_redir(redir_host, redir_port)
|
|
93
|
+
new_a_infod(redir_port)
|
|
94
|
+
new_a_memd(memd_port)
|
|
95
|
+
new_a_rsvd(tspd_host, tspd_port)
|
|
96
|
+
new_a_tspd(tspd_host, tspd_port)
|
|
115
97
|
new_a_proxy
|
|
98
|
+
new_a_big
|
|
116
99
|
end
|
|
117
100
|
|
|
118
101
|
def looping
|
|
@@ -120,67 +103,61 @@ module Girl
|
|
|
120
103
|
loop_heartbeat
|
|
121
104
|
|
|
122
105
|
loop do
|
|
123
|
-
rs, ws = IO.select(
|
|
106
|
+
rs, ws = IO.select(@reads, @writes)
|
|
124
107
|
|
|
125
|
-
rs.each do |
|
|
126
|
-
role = @roles[
|
|
108
|
+
rs.each do |sock|
|
|
109
|
+
role = @roles[sock]
|
|
127
110
|
|
|
128
111
|
case role
|
|
129
|
-
when :
|
|
130
|
-
|
|
131
|
-
when :
|
|
132
|
-
|
|
133
|
-
when :
|
|
134
|
-
|
|
135
|
-
when :infod
|
|
136
|
-
read_infod(
|
|
137
|
-
when :mem
|
|
138
|
-
read_mem(
|
|
139
|
-
when :memd
|
|
140
|
-
read_memd(
|
|
141
|
-
when :p1
|
|
142
|
-
read_p1(
|
|
143
|
-
when :proxy
|
|
144
|
-
read_proxy(
|
|
145
|
-
when :redir
|
|
146
|
-
read_redir(
|
|
147
|
-
when :
|
|
148
|
-
|
|
149
|
-
when :
|
|
150
|
-
|
|
151
|
-
when :
|
|
152
|
-
|
|
153
|
-
when :
|
|
154
|
-
|
|
155
|
-
when :src then
|
|
156
|
-
read_src( sock )
|
|
157
|
-
when :tspd then
|
|
158
|
-
read_tspd( sock )
|
|
112
|
+
when :big
|
|
113
|
+
read_big(sock)
|
|
114
|
+
when :dns
|
|
115
|
+
read_dns(sock)
|
|
116
|
+
when :dst
|
|
117
|
+
read_dst(sock)
|
|
118
|
+
when :infod
|
|
119
|
+
read_infod(sock)
|
|
120
|
+
when :mem
|
|
121
|
+
read_mem(sock)
|
|
122
|
+
when :memd
|
|
123
|
+
read_memd(sock)
|
|
124
|
+
when :p1
|
|
125
|
+
read_p1(sock)
|
|
126
|
+
when :proxy
|
|
127
|
+
read_proxy(sock)
|
|
128
|
+
when :redir
|
|
129
|
+
read_redir(sock)
|
|
130
|
+
when :rsv
|
|
131
|
+
read_rsv(sock)
|
|
132
|
+
when :rsvd
|
|
133
|
+
read_rsvd(sock)
|
|
134
|
+
when :src
|
|
135
|
+
read_src(sock)
|
|
136
|
+
when :tspd
|
|
137
|
+
read_tspd(sock)
|
|
159
138
|
else
|
|
160
|
-
close_sock(
|
|
139
|
+
close_sock(sock)
|
|
161
140
|
end
|
|
162
141
|
end
|
|
163
142
|
|
|
164
|
-
ws.each do |
|
|
165
|
-
role = @roles[
|
|
143
|
+
ws.each do |sock|
|
|
144
|
+
role = @roles[sock]
|
|
166
145
|
|
|
167
146
|
case role
|
|
168
|
-
when :
|
|
169
|
-
|
|
170
|
-
when :
|
|
171
|
-
|
|
172
|
-
when :mem
|
|
173
|
-
write_mem(
|
|
174
|
-
when :p1
|
|
175
|
-
write_p1(
|
|
176
|
-
when :proxy
|
|
177
|
-
write_proxy(
|
|
178
|
-
when :
|
|
179
|
-
|
|
180
|
-
when :src then
|
|
181
|
-
write_src( sock )
|
|
147
|
+
when :big
|
|
148
|
+
write_big(sock)
|
|
149
|
+
when :dst
|
|
150
|
+
write_dst(sock)
|
|
151
|
+
when :mem
|
|
152
|
+
write_mem(sock)
|
|
153
|
+
when :p1
|
|
154
|
+
write_p1(sock)
|
|
155
|
+
when :proxy
|
|
156
|
+
write_proxy(sock)
|
|
157
|
+
when :src
|
|
158
|
+
write_src(sock)
|
|
182
159
|
else
|
|
183
|
-
close_sock(
|
|
160
|
+
close_sock(sock)
|
|
184
161
|
end
|
|
185
162
|
end
|
|
186
163
|
end
|
|
@@ -195,587 +172,590 @@ module Girl
|
|
|
195
172
|
|
|
196
173
|
private
|
|
197
174
|
|
|
198
|
-
def
|
|
199
|
-
return if
|
|
200
|
-
|
|
201
|
-
|
|
202
|
-
bytesize =
|
|
175
|
+
def add_big_wbuff(data)
|
|
176
|
+
return if @big.nil? || @big.closed? || data.nil? || data.empty?
|
|
177
|
+
big_info = @big_infos[@big]
|
|
178
|
+
big_info[:wbuff] << data
|
|
179
|
+
bytesize = big_info[:wbuff].bytesize
|
|
203
180
|
|
|
204
|
-
if bytesize >= CLOSE_ABOVE
|
|
205
|
-
puts "close overflow
|
|
206
|
-
|
|
181
|
+
if bytesize >= CLOSE_ABOVE
|
|
182
|
+
puts "close overflow big"
|
|
183
|
+
close_big(@big)
|
|
207
184
|
return
|
|
208
185
|
end
|
|
209
186
|
|
|
210
|
-
if !
|
|
211
|
-
puts "
|
|
212
|
-
|
|
213
|
-
|
|
187
|
+
if !big_info[:overflowing] && (bytesize >= WBUFF_LIMIT)
|
|
188
|
+
puts "big overflow"
|
|
189
|
+
big_info[:overflowing] = true
|
|
190
|
+
|
|
191
|
+
@src_infos.select{|_, info| info[:is_big]}.each do |src, info|
|
|
192
|
+
puts "pause src #{info[:destination_domain]}"
|
|
193
|
+
@reads.delete(src)
|
|
194
|
+
end
|
|
195
|
+
|
|
196
|
+
@p1_infos.select{|_, info| info[:is_big]}.each do |p1, info|
|
|
197
|
+
puts "pause p1 #{info[:p2_id]}"
|
|
198
|
+
@reads.delete(p1)
|
|
199
|
+
end
|
|
214
200
|
end
|
|
215
201
|
|
|
216
|
-
add_write(
|
|
202
|
+
add_write(@big)
|
|
217
203
|
end
|
|
218
204
|
|
|
219
|
-
def
|
|
220
|
-
return if
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
bytesize =
|
|
205
|
+
def add_dst_wbuff(dst, data)
|
|
206
|
+
return if dst.nil? || dst.closed? || data.nil? || data.empty?
|
|
207
|
+
dst_info = @dst_infos[dst]
|
|
208
|
+
dst_info[:wbuff] << data
|
|
209
|
+
bytesize = dst_info[:wbuff].bytesize
|
|
210
|
+
domain = dst_info[:domain]
|
|
224
211
|
|
|
225
|
-
if bytesize >= CLOSE_ABOVE
|
|
226
|
-
puts "close overflow
|
|
227
|
-
|
|
212
|
+
if bytesize >= CLOSE_ABOVE
|
|
213
|
+
puts "close overflow dst #{domain}"
|
|
214
|
+
close_dst(dst)
|
|
228
215
|
return
|
|
229
216
|
end
|
|
230
217
|
|
|
231
|
-
if !
|
|
232
|
-
puts "
|
|
233
|
-
|
|
234
|
-
|
|
218
|
+
if !dst_info[:overflowing] && (bytesize >= WBUFF_LIMIT)
|
|
219
|
+
puts "dst overflow #{domain}"
|
|
220
|
+
dst_info[:overflowing] = true
|
|
221
|
+
puts "pause src"
|
|
222
|
+
@reads.delete(dst_info[:src])
|
|
235
223
|
end
|
|
236
224
|
|
|
237
|
-
add_write(
|
|
225
|
+
add_write(dst)
|
|
238
226
|
end
|
|
239
227
|
|
|
240
|
-
def add_mem_wbuff(
|
|
228
|
+
def add_mem_wbuff(mem, data)
|
|
241
229
|
return if mem.nil? || mem.closed? || data.nil? || data.empty?
|
|
242
|
-
mem_info = @mem_infos[
|
|
243
|
-
mem_info[
|
|
244
|
-
add_write(
|
|
230
|
+
mem_info = @mem_infos[mem]
|
|
231
|
+
mem_info[:wbuff] << data
|
|
232
|
+
add_write(mem)
|
|
245
233
|
end
|
|
246
234
|
|
|
247
|
-
def add_p1_wbuff(
|
|
235
|
+
def add_p1_wbuff(p1, data)
|
|
248
236
|
return if p1.nil? || p1.closed? || data.nil? || data.empty?
|
|
249
|
-
p1_info = @p1_infos[
|
|
250
|
-
p1_info[
|
|
251
|
-
bytesize = p1_info[
|
|
252
|
-
p2_id = p1_info[
|
|
237
|
+
p1_info = @p1_infos[p1]
|
|
238
|
+
p1_info[:wbuff] << data
|
|
239
|
+
bytesize = p1_info[:wbuff].bytesize
|
|
240
|
+
p2_id = p1_info[:p2_id]
|
|
253
241
|
|
|
254
|
-
if bytesize >= CLOSE_ABOVE
|
|
255
|
-
puts "close overflow p1 #{
|
|
256
|
-
close_p1(
|
|
242
|
+
if bytesize >= CLOSE_ABOVE
|
|
243
|
+
puts "close overflow p1 #{p2_id}"
|
|
244
|
+
close_p1(p1)
|
|
257
245
|
return
|
|
258
246
|
end
|
|
259
247
|
|
|
260
|
-
if !p1_info[
|
|
261
|
-
puts "
|
|
262
|
-
|
|
263
|
-
|
|
264
|
-
|
|
248
|
+
if !p1_info[:overflowing] && (bytesize >= WBUFF_LIMIT)
|
|
249
|
+
puts "p1 overflow #{p2_id}"
|
|
250
|
+
p1_info[:overflowing] = true
|
|
251
|
+
|
|
252
|
+
if @big
|
|
253
|
+
puts 'pause big'
|
|
254
|
+
@reads.delete(@big)
|
|
255
|
+
end
|
|
265
256
|
end
|
|
266
257
|
|
|
267
|
-
add_write(
|
|
258
|
+
add_write(p1)
|
|
268
259
|
end
|
|
269
260
|
|
|
270
|
-
def add_proxy_wbuff(
|
|
261
|
+
def add_proxy_wbuff(data)
|
|
271
262
|
return if @proxy.closed? || data.nil? || data.empty?
|
|
272
|
-
proxy_info = @proxy_infos[
|
|
273
|
-
proxy_info[
|
|
274
|
-
bytesize = proxy_info[
|
|
263
|
+
proxy_info = @proxy_infos[@proxy]
|
|
264
|
+
proxy_info[:wbuff] << data
|
|
265
|
+
bytesize = proxy_info[:wbuff].bytesize
|
|
275
266
|
|
|
276
|
-
if bytesize >= CLOSE_ABOVE
|
|
267
|
+
if bytesize >= CLOSE_ABOVE
|
|
277
268
|
puts "close overflow proxy"
|
|
278
|
-
close_proxy(
|
|
269
|
+
close_proxy(@proxy)
|
|
279
270
|
return
|
|
280
271
|
end
|
|
281
272
|
|
|
282
|
-
add_write(
|
|
273
|
+
add_write(@proxy)
|
|
283
274
|
end
|
|
284
275
|
|
|
285
|
-
def add_read(
|
|
286
|
-
return if sock.nil? || sock.closed? || @reads.include?(
|
|
276
|
+
def add_read(sock, role = nil)
|
|
277
|
+
return if sock.nil? || sock.closed? || @reads.include?(sock)
|
|
287
278
|
@reads << sock
|
|
288
279
|
|
|
289
|
-
if role
|
|
290
|
-
@roles[
|
|
280
|
+
if role
|
|
281
|
+
@roles[sock] = role
|
|
291
282
|
else
|
|
292
|
-
role = @roles[
|
|
283
|
+
role = @roles[sock]
|
|
293
284
|
end
|
|
294
285
|
|
|
295
|
-
if @update_roles.include?(
|
|
296
|
-
set_update( sock )
|
|
297
|
-
end
|
|
286
|
+
set_update(sock) if @update_roles.include?(role)
|
|
298
287
|
end
|
|
299
288
|
|
|
300
|
-
def
|
|
301
|
-
return if relay.nil? || relay.closed? || data.nil? || data.empty?
|
|
302
|
-
relay_info = @relay_infos[ relay ]
|
|
303
|
-
relay_info[ :wbuff ] << data
|
|
304
|
-
bytesize = relay_info[ :wbuff ].bytesize
|
|
305
|
-
|
|
306
|
-
if bytesize >= CLOSE_ABOVE then
|
|
307
|
-
puts "close overflow relay #{ relay_info[ :addrinfo ].ip_unpack.inspect }"
|
|
308
|
-
close_relay( relay )
|
|
309
|
-
return
|
|
310
|
-
end
|
|
311
|
-
|
|
312
|
-
if !relay_info[ :overflowing ] && ( bytesize >= WBUFF_LIMIT ) then
|
|
313
|
-
puts "relay overflow pause girl #{ relay_info[ :addrinfo ].ip_unpack.inspect }"
|
|
314
|
-
@reads.delete( relay_info[ :girl ] )
|
|
315
|
-
relay_info[ :overflowing ] = true
|
|
316
|
-
end
|
|
317
|
-
|
|
318
|
-
add_write( relay )
|
|
319
|
-
end
|
|
320
|
-
|
|
321
|
-
def add_socks5_conn_reply( src )
|
|
289
|
+
def add_socks5_conn_reply(src)
|
|
322
290
|
# +----+-----+-------+------+----------+----------+
|
|
323
291
|
# |VER | REP | RSV | ATYP | BND.ADDR | BND.PORT |
|
|
324
292
|
# +----+-----+-------+------+----------+----------+
|
|
325
293
|
# | 1 | 1 | X'00' | 1 | Variable | 2 |
|
|
326
294
|
# +----+-----+-------+------+----------+----------+
|
|
327
295
|
redir_ip, redir_port = @redir_local_address.ip_unpack
|
|
328
|
-
data = [
|
|
329
|
-
add_src_wbuff(
|
|
296
|
+
data = [[5, 0, 0, 1].pack('C4'), IPAddr.new(redir_ip).hton, [redir_port].pack('n')].join
|
|
297
|
+
add_src_wbuff(src, data)
|
|
330
298
|
end
|
|
331
299
|
|
|
332
|
-
def add_src_rbuff(
|
|
300
|
+
def add_src_rbuff(src, data)
|
|
333
301
|
return if src.nil? || src.closed? || data.nil? || data.empty?
|
|
334
|
-
src_info = @src_infos[
|
|
335
|
-
puts "add src rbuff #{
|
|
336
|
-
src_info[
|
|
302
|
+
src_info = @src_infos[src]
|
|
303
|
+
puts "add src rbuff #{data.bytesize}" if @is_debug
|
|
304
|
+
src_info[:rbuff] << data
|
|
337
305
|
|
|
338
|
-
if src_info[
|
|
306
|
+
if src_info[:rbuff].bytesize >= WBUFF_LIMIT
|
|
339
307
|
puts "src rbuff full"
|
|
340
|
-
close_src(
|
|
308
|
+
close_src(src)
|
|
341
309
|
end
|
|
342
310
|
end
|
|
343
311
|
|
|
344
|
-
def add_src_wbuff(
|
|
312
|
+
def add_src_wbuff(src, data)
|
|
345
313
|
return if src.nil? || src.closed? || data.nil? || data.empty?
|
|
346
|
-
src_info = @src_infos[
|
|
347
|
-
src_info[
|
|
348
|
-
bytesize = src_info[
|
|
349
|
-
src_id = src_info[
|
|
350
|
-
domain = src_info[
|
|
351
|
-
|
|
352
|
-
if bytesize >= CLOSE_ABOVE then
|
|
353
|
-
puts "close overflow src #{ src_id } #{ domain }"
|
|
354
|
-
close_src( src )
|
|
355
|
-
return
|
|
356
|
-
end
|
|
357
|
-
|
|
358
|
-
if !src_info[ :overflowing ] && ( bytesize >= WBUFF_LIMIT ) then
|
|
359
|
-
if src_info[ :proxy_type ] == :direct then
|
|
360
|
-
puts "src overflow pause dst #{ src_id } #{ domain }"
|
|
361
|
-
@reads.delete( src_info[ :dst ] )
|
|
362
|
-
elsif src_info[ :proxy_type ] == :remote then
|
|
363
|
-
puts "add h_src_overflow #{ src_id } #{ domain }"
|
|
364
|
-
msg = "#{ @h_src_overflow }#{ [ src_id ].pack( 'Q>' ) }"
|
|
365
|
-
add_proxy_wbuff( pack_a_chunk( msg ) )
|
|
366
|
-
end
|
|
314
|
+
src_info = @src_infos[src]
|
|
315
|
+
src_info[:wbuff] << data
|
|
316
|
+
bytesize = src_info[:wbuff].bytesize
|
|
317
|
+
src_id = src_info[:src_id]
|
|
318
|
+
domain = src_info[:destination_domain]
|
|
367
319
|
|
|
368
|
-
|
|
320
|
+
if bytesize >= CLOSE_ABOVE
|
|
321
|
+
puts "close overflow src #{src_id} #{domain}"
|
|
322
|
+
close_src(src)
|
|
323
|
+
return
|
|
369
324
|
end
|
|
370
325
|
|
|
371
|
-
|
|
326
|
+
if !src_info[:overflowing] && (bytesize >= WBUFF_LIMIT)
|
|
327
|
+
puts "src overflow #{src_id} #{domain}"
|
|
328
|
+
src_info[:overflowing] = true
|
|
329
|
+
|
|
330
|
+
if src_info[:proxy_type] == :direct
|
|
331
|
+
puts "pause dst"
|
|
332
|
+
@reads.delete(src_info[:dst])
|
|
333
|
+
elsif src_info[:proxy_type] == :remote
|
|
334
|
+
puts "pause big"
|
|
335
|
+
@reads.delete(@big)
|
|
336
|
+
end
|
|
337
|
+
end
|
|
338
|
+
|
|
339
|
+
add_write(src)
|
|
372
340
|
end
|
|
373
341
|
|
|
374
|
-
def add_write(
|
|
375
|
-
return if sock.nil? || sock.closed? || @writes.include?(
|
|
342
|
+
def add_write(sock)
|
|
343
|
+
return if sock.nil? || sock.closed? || @writes.include?(sock)
|
|
376
344
|
@writes << sock
|
|
377
|
-
role = @roles[
|
|
378
|
-
|
|
379
|
-
if @update_roles.include?( role ) then
|
|
380
|
-
set_update( sock )
|
|
381
|
-
end
|
|
345
|
+
role = @roles[sock]
|
|
346
|
+
set_update(sock) if @update_roles.include?(role)
|
|
382
347
|
end
|
|
383
348
|
|
|
384
349
|
def check_expire_dnses
|
|
385
350
|
now = Time.new
|
|
386
351
|
|
|
387
|
-
@dns_infos.select{
|
|
388
|
-
puts "expire dns #{
|
|
389
|
-
close_dns(
|
|
352
|
+
@dns_infos.select{|dns, _| now.to_i - @updates[dns].to_i >= @expire_short_after}.each do |dns, info|
|
|
353
|
+
puts "expire dns #{info[:domain]}" if @is_debug
|
|
354
|
+
close_dns(dns)
|
|
390
355
|
end
|
|
391
356
|
end
|
|
392
357
|
|
|
393
358
|
def check_expire_dsts
|
|
394
359
|
now = Time.new
|
|
395
360
|
|
|
396
|
-
@dst_infos.select{
|
|
397
|
-
puts "expire dst #{
|
|
398
|
-
close_dst(
|
|
399
|
-
end
|
|
400
|
-
end
|
|
401
|
-
|
|
402
|
-
def check_expire_girls
|
|
403
|
-
now = Time.new
|
|
404
|
-
|
|
405
|
-
@girl_infos.select{ | girl, info | info[ :connected ] ? ( now.to_i - @updates[ girl ].to_i >= @expire_long_after ) : ( now.to_i - @updates[ girl ].to_i >= @expire_connecting ) }.each do | girl, _ |
|
|
406
|
-
puts "expire girl" if @is_debug
|
|
407
|
-
close_girl( girl )
|
|
361
|
+
@dst_infos.select{|dst, info| info[:connected] ? (now.to_i - @updates[dst].to_i >= @expire_long_after) : (now.to_i - @updates[dst].to_i >= @expire_connecting)}.each do |dst, info|
|
|
362
|
+
puts "expire dst #{info[:domain]}" if @is_debug
|
|
363
|
+
close_dst(dst)
|
|
408
364
|
end
|
|
409
365
|
end
|
|
410
366
|
|
|
411
367
|
def check_expire_mems
|
|
412
368
|
now = Time.new
|
|
413
369
|
|
|
414
|
-
@mem_infos.select{
|
|
370
|
+
@mem_infos.select{|mem, _| now.to_i - @updates[mem].to_i >= @expire_short_after}.each do |mem, _|
|
|
415
371
|
puts "expire mem" if @is_debug
|
|
416
|
-
close_mem(
|
|
372
|
+
close_mem(mem)
|
|
417
373
|
end
|
|
418
374
|
end
|
|
419
375
|
|
|
420
376
|
def check_expire_nears
|
|
421
377
|
now = Time.new
|
|
422
378
|
|
|
423
|
-
@near_infos.select{
|
|
424
|
-
puts "expire near #{
|
|
425
|
-
@near_infos.delete(
|
|
379
|
+
@near_infos.select{|_, info| now.to_i - info[:created_at].to_i >= @expire_short_after}.each do |near_id, info|
|
|
380
|
+
puts "expire near #{info[:domain]}" if @is_debug
|
|
381
|
+
@near_infos.delete(near_id)
|
|
426
382
|
end
|
|
427
383
|
end
|
|
428
384
|
|
|
429
385
|
def check_expire_p1s
|
|
430
386
|
now = Time.new
|
|
431
387
|
|
|
432
|
-
@p1_infos.select{
|
|
433
|
-
puts "expire p1 #{
|
|
434
|
-
close_p1(
|
|
435
|
-
end
|
|
436
|
-
end
|
|
437
|
-
|
|
438
|
-
def check_expire_relays
|
|
439
|
-
now = Time.new
|
|
440
|
-
|
|
441
|
-
@relay_infos.select{ | relay, _ | now.to_i - @updates[ relay ].to_i >= @expire_long_after }.each do | relay, info |
|
|
442
|
-
puts "expire relay #{ info[ :addrinfo ].ip_unpack.inspect }" if @is_debug
|
|
443
|
-
close_relay( relay )
|
|
388
|
+
@p1_infos.select{|p1, info| info[:connected] ? (now.to_i - @updates[p1].to_i >= @expire_long_after) : (now.to_i - @updates[p1].to_i >= @expire_connecting)}.each do |p1, info|
|
|
389
|
+
puts "expire p1 #{info[:p2_id]}" if @is_debug
|
|
390
|
+
close_p1(p1)
|
|
444
391
|
end
|
|
445
392
|
end
|
|
446
393
|
|
|
447
394
|
def check_expire_rsvs
|
|
448
395
|
now = Time.new
|
|
449
396
|
|
|
450
|
-
@rsv_infos.select{
|
|
451
|
-
puts "expire rsv #{
|
|
452
|
-
close_rsv(
|
|
397
|
+
@rsv_infos.select{|rsv, _| now.to_i - @updates[rsv].to_i >= @expire_short_after}.each do |rsv, info|
|
|
398
|
+
puts "expire rsv #{info[:domain]}" if @is_debug
|
|
399
|
+
close_rsv(rsv)
|
|
453
400
|
end
|
|
454
401
|
end
|
|
455
402
|
|
|
456
403
|
def check_expire_srcs
|
|
457
404
|
now = Time.new
|
|
458
405
|
|
|
459
|
-
@src_infos.select{
|
|
460
|
-
puts "expire src #{
|
|
461
|
-
close_src(
|
|
406
|
+
@src_infos.select{|src, _| now.to_i - @updates[src].to_i >= @expire_long_after}.each do |src, info|
|
|
407
|
+
puts "expire src #{info[:destination_domain]}" if @is_debug
|
|
408
|
+
close_src(src)
|
|
462
409
|
end
|
|
463
410
|
end
|
|
464
411
|
|
|
465
|
-
def
|
|
412
|
+
def close_big(big)
|
|
413
|
+
return if big.nil? || big.closed?
|
|
414
|
+
close_sock(big)
|
|
415
|
+
big_info = @big_infos.delete(big)
|
|
416
|
+
puts "close big"
|
|
417
|
+
big_info
|
|
418
|
+
end
|
|
419
|
+
|
|
420
|
+
def close_dns(dns)
|
|
466
421
|
return nil if dns.nil? || dns.closed?
|
|
467
|
-
close_sock(
|
|
468
|
-
dns_info = @dns_infos.delete(
|
|
469
|
-
|
|
422
|
+
close_sock(dns)
|
|
423
|
+
dns_info = @dns_infos.delete(dns)
|
|
424
|
+
|
|
425
|
+
if dns_info
|
|
426
|
+
domain = dns_info[:domain]
|
|
427
|
+
puts "close dns #{domain}" if @is_debug
|
|
428
|
+
end
|
|
429
|
+
|
|
470
430
|
dns_info
|
|
471
431
|
end
|
|
472
432
|
|
|
473
|
-
def close_dst(
|
|
433
|
+
def close_dst(dst)
|
|
474
434
|
return nil if dst.nil? || dst.closed?
|
|
475
|
-
close_sock(
|
|
476
|
-
dst_info = @dst_infos.delete(
|
|
477
|
-
|
|
478
|
-
|
|
479
|
-
|
|
480
|
-
|
|
435
|
+
close_sock(dst)
|
|
436
|
+
dst_info = @dst_infos.delete(dst)
|
|
437
|
+
|
|
438
|
+
if dst_info
|
|
439
|
+
domain = dst_info[:domain]
|
|
440
|
+
puts "close dst #{domain}" if @is_debug
|
|
441
|
+
set_src_closing(dst_info[:src])
|
|
442
|
+
end
|
|
481
443
|
|
|
482
|
-
|
|
483
|
-
return nil if girl.nil? || girl.closed?
|
|
484
|
-
close_sock( girl )
|
|
485
|
-
girl_info = @girl_infos.delete( girl )
|
|
486
|
-
puts "close girl" if @is_debug
|
|
487
|
-
set_relay_closing( girl_info[ :relay ] ) if girl_info
|
|
488
|
-
girl_info
|
|
444
|
+
dst_info
|
|
489
445
|
end
|
|
490
446
|
|
|
491
|
-
def close_mem(
|
|
447
|
+
def close_mem(mem)
|
|
492
448
|
return nil if mem.nil? || mem.closed?
|
|
493
|
-
close_sock(
|
|
494
|
-
@mem_infos.delete(
|
|
449
|
+
close_sock(mem)
|
|
450
|
+
@mem_infos.delete(mem)
|
|
495
451
|
end
|
|
496
452
|
|
|
497
|
-
def close_p1(
|
|
453
|
+
def close_p1(p1)
|
|
498
454
|
return nil if p1.nil? || p1.closed?
|
|
499
|
-
close_sock(
|
|
500
|
-
p1_info = @p1_infos.delete(
|
|
455
|
+
close_sock(p1)
|
|
456
|
+
p1_info = @p1_infos.delete(p1)
|
|
501
457
|
|
|
502
|
-
|
|
503
|
-
|
|
504
|
-
|
|
505
|
-
|
|
506
|
-
|
|
507
|
-
msg = "#{ @h_p1_close }#{ [ p2_id ].pack( 'Q>' ) }"
|
|
508
|
-
add_proxy_wbuff( pack_a_chunk( msg ) )
|
|
458
|
+
if p1_info
|
|
459
|
+
p2_id = p1_info[:p2_id]
|
|
460
|
+
puts "add h_p1_close #{p2_id}"
|
|
461
|
+
msg = "#{@h_p1_close}#{[p2_id].pack('Q>')}"
|
|
462
|
+
add_proxy_wbuff(pack_a_chunk(msg))
|
|
509
463
|
end
|
|
510
464
|
|
|
511
465
|
p1_info
|
|
512
466
|
end
|
|
513
467
|
|
|
514
|
-
def close_proxy(
|
|
468
|
+
def close_proxy(proxy)
|
|
515
469
|
return if proxy.nil? || proxy.closed?
|
|
516
|
-
close_sock(
|
|
517
|
-
proxy_info = @proxy_infos.delete(
|
|
470
|
+
close_sock(proxy)
|
|
471
|
+
proxy_info = @proxy_infos.delete(proxy)
|
|
518
472
|
puts "close proxy"
|
|
519
|
-
@src_infos.each{
|
|
520
|
-
@p1_infos.each{
|
|
473
|
+
@src_infos.each{|src, _| close_src(src)}
|
|
474
|
+
@p1_infos.each{|p1, _| close_p1(p1)}
|
|
521
475
|
proxy_info
|
|
522
476
|
end
|
|
523
477
|
|
|
524
|
-
def
|
|
525
|
-
return nil if relay.nil? || relay.closed?
|
|
526
|
-
close_sock( relay )
|
|
527
|
-
relay_info = @relay_infos.delete( relay )
|
|
528
|
-
puts "close relay" if @is_debug
|
|
529
|
-
set_girl_closing( relay_info[ :girl ] ) if relay_info
|
|
530
|
-
relay_info
|
|
531
|
-
end
|
|
532
|
-
|
|
533
|
-
def close_rsv( rsv )
|
|
478
|
+
def close_rsv(rsv)
|
|
534
479
|
return nil if rsv.nil? || rsv.closed?
|
|
535
|
-
close_sock(
|
|
536
|
-
rsv_info = @rsv_infos.delete(
|
|
537
|
-
|
|
480
|
+
close_sock(rsv)
|
|
481
|
+
rsv_info = @rsv_infos.delete(rsv)
|
|
482
|
+
|
|
483
|
+
if rsv_info
|
|
484
|
+
domain = rsv_info[:domain]
|
|
485
|
+
puts "close rsv #{domain}" if @is_debug
|
|
486
|
+
end
|
|
487
|
+
|
|
538
488
|
rsv_info
|
|
539
489
|
end
|
|
540
490
|
|
|
541
|
-
def close_sock(
|
|
491
|
+
def close_sock(sock)
|
|
542
492
|
return if sock.nil? || sock.closed?
|
|
543
493
|
sock.close
|
|
544
|
-
@reads.delete(
|
|
545
|
-
@writes.delete(
|
|
546
|
-
@updates.delete(
|
|
547
|
-
@roles.delete(
|
|
494
|
+
@reads.delete(sock)
|
|
495
|
+
@writes.delete(sock)
|
|
496
|
+
@updates.delete(sock)
|
|
497
|
+
@roles.delete(sock)
|
|
548
498
|
end
|
|
549
499
|
|
|
550
|
-
def close_src(
|
|
500
|
+
def close_src(src)
|
|
551
501
|
return nil if src.nil? || src.closed?
|
|
552
|
-
close_sock(
|
|
553
|
-
src_info = @src_infos.delete(
|
|
554
|
-
|
|
555
|
-
|
|
556
|
-
|
|
557
|
-
|
|
558
|
-
|
|
559
|
-
|
|
560
|
-
|
|
561
|
-
|
|
562
|
-
|
|
563
|
-
|
|
564
|
-
|
|
565
|
-
|
|
502
|
+
close_sock(src)
|
|
503
|
+
src_info = @src_infos.delete(src)
|
|
504
|
+
|
|
505
|
+
if src_info
|
|
506
|
+
src_id = src_info[:src_id]
|
|
507
|
+
domain = src_info[:destination_domain]
|
|
508
|
+
proxy_type = src_info[:proxy_type]
|
|
509
|
+
puts "close src #{domain}" if @is_debug
|
|
510
|
+
|
|
511
|
+
if proxy_type == :direct
|
|
512
|
+
set_dst_closing(src_info[:dst])
|
|
513
|
+
elsif proxy_type == :remote
|
|
514
|
+
puts "add h_src_close #{src_id}" if @is_debug
|
|
515
|
+
msg = "#{@h_src_close}#{[src_id].pack('Q>')}"
|
|
516
|
+
add_proxy_wbuff(pack_a_chunk(msg))
|
|
517
|
+
end
|
|
566
518
|
end
|
|
567
519
|
|
|
568
520
|
src_info
|
|
569
521
|
end
|
|
570
522
|
|
|
571
|
-
def
|
|
572
|
-
return if data.nil? || data.empty? || @
|
|
573
|
-
|
|
523
|
+
def deal_big_msg(data)
|
|
524
|
+
return if data.nil? || data.empty? || @big.closed?
|
|
525
|
+
big_info = @big_infos[@big]
|
|
574
526
|
now = Time.new
|
|
575
|
-
|
|
576
|
-
h = data[
|
|
527
|
+
big_info[:recv_at] = now
|
|
528
|
+
h = data[0]
|
|
577
529
|
|
|
578
530
|
case h
|
|
579
|
-
when @
|
|
531
|
+
when @h_p2_traffic
|
|
580
532
|
return if data.bytesize < 9
|
|
581
|
-
p2_id = data[
|
|
582
|
-
|
|
583
|
-
|
|
584
|
-
|
|
533
|
+
p2_id = data[1, 8].unpack('Q>').first
|
|
534
|
+
data = data[9..-1]
|
|
535
|
+
# puts "big got h_p2_traffic #{p2_id} #{data.bytesize}" if @is_debug
|
|
536
|
+
p1, _ = @p1_infos.find{|_, info| info[:p2_id] == p2_id}
|
|
537
|
+
add_p1_wbuff(p1, data)
|
|
538
|
+
when @h_traffic
|
|
585
539
|
return if data.bytesize < 9
|
|
586
|
-
src_id = data[
|
|
587
|
-
|
|
588
|
-
|
|
589
|
-
|
|
590
|
-
|
|
591
|
-
|
|
592
|
-
|
|
540
|
+
src_id = data[1, 8].unpack('Q>').first
|
|
541
|
+
data = data[9..-1]
|
|
542
|
+
# puts "big got h_traffic #{src_id} #{data.bytesize}" if @is_debug
|
|
543
|
+
src, _ = @src_infos.find{|_, info| info[:src_id] == src_id}
|
|
544
|
+
add_src_wbuff(src, data)
|
|
545
|
+
end
|
|
546
|
+
end
|
|
547
|
+
|
|
548
|
+
def deal_msg(data)
|
|
549
|
+
return if data.nil? || data.empty? || @proxy.closed?
|
|
550
|
+
proxy_info = @proxy_infos[@proxy]
|
|
551
|
+
now = Time.new
|
|
552
|
+
proxy_info[:recv_at] = now
|
|
553
|
+
h = data[0]
|
|
554
|
+
|
|
555
|
+
case h
|
|
556
|
+
when @h_a_new_p2
|
|
593
557
|
return if data.bytesize < 9
|
|
594
|
-
p2_id = data[
|
|
595
|
-
puts "got
|
|
596
|
-
|
|
597
|
-
|
|
598
|
-
when @h_p2_traffic then
|
|
558
|
+
p2_id = data[1, 8].unpack('Q>').first
|
|
559
|
+
puts "got h_a_new_p2 #{p2_id}"
|
|
560
|
+
new_a_p1(p2_id)
|
|
561
|
+
when @h_dst_close
|
|
599
562
|
return if data.bytesize < 9
|
|
600
|
-
|
|
601
|
-
|
|
602
|
-
|
|
603
|
-
|
|
604
|
-
|
|
605
|
-
when @h_p2_overflow then
|
|
563
|
+
src_id = data[1, 8].unpack('Q>').first
|
|
564
|
+
puts "got h_dst_close #{src_id}" if @is_debug
|
|
565
|
+
src, _ = @src_infos.find{|_, info| info[:src_id] == src_id}
|
|
566
|
+
set_src_closing(src)
|
|
567
|
+
when @h_p2_close
|
|
606
568
|
return if data.bytesize < 9
|
|
607
|
-
p2_id = data[
|
|
608
|
-
puts "got
|
|
609
|
-
p1, _ = @p1_infos.find{
|
|
610
|
-
|
|
611
|
-
|
|
612
|
-
when @h_p2_underhalf then
|
|
569
|
+
p2_id = data[1, 8].unpack('Q>').first
|
|
570
|
+
puts "got h_p2_close #{p2_id}"
|
|
571
|
+
p1, _ = @p1_infos.find{|_, info| info[:p2_id] == p2_id}
|
|
572
|
+
set_p1_closing(p1)
|
|
573
|
+
when @h_p2_traffic
|
|
613
574
|
return if data.bytesize < 9
|
|
614
|
-
p2_id = data[
|
|
615
|
-
|
|
616
|
-
p1, _ = @p1_infos.find{
|
|
617
|
-
|
|
618
|
-
when @h_response
|
|
575
|
+
p2_id = data[1, 8].unpack('Q>').first
|
|
576
|
+
data = data[9..-1]
|
|
577
|
+
p1, _ = @p1_infos.find{|_, info| info[:p2_id] == p2_id}
|
|
578
|
+
add_p1_wbuff(p1, data)
|
|
579
|
+
when @h_response
|
|
619
580
|
return if data.bytesize < 3
|
|
620
|
-
near_id = data[
|
|
621
|
-
data = data[
|
|
622
|
-
puts "got h_response #{
|
|
623
|
-
near_info = @near_infos.delete(
|
|
581
|
+
near_id = data[1, 8].unpack('Q>').first
|
|
582
|
+
data = data[9..-1]
|
|
583
|
+
puts "got h_response #{near_id} #{data.bytesize}" if @is_debug
|
|
584
|
+
near_info = @near_infos.delete(near_id)
|
|
624
585
|
|
|
625
|
-
if near_info
|
|
626
|
-
data[
|
|
627
|
-
addrinfo = near_info[
|
|
628
|
-
send_data(
|
|
586
|
+
if near_info
|
|
587
|
+
data[0, 2] = near_info[:id]
|
|
588
|
+
addrinfo = near_info[:addrinfo]
|
|
589
|
+
send_data(@rsvd, data, addrinfo)
|
|
629
590
|
|
|
630
591
|
begin
|
|
631
|
-
ip = seek_ip(
|
|
592
|
+
ip = seek_ip(data)
|
|
632
593
|
rescue Exception => e
|
|
633
|
-
puts "response seek ip #{
|
|
594
|
+
puts "response seek ip #{e.class} #{e.message}"
|
|
634
595
|
end
|
|
635
596
|
|
|
636
|
-
if ip
|
|
637
|
-
domain = near_info[
|
|
638
|
-
type = near_info[
|
|
597
|
+
if ip
|
|
598
|
+
domain = near_info[:domain]
|
|
599
|
+
type = near_info[:type]
|
|
639
600
|
|
|
640
|
-
if type == 1
|
|
641
|
-
@response_caches[
|
|
601
|
+
if type == 1
|
|
602
|
+
@response_caches[domain] = [data, now, ip, true]
|
|
642
603
|
else
|
|
643
|
-
@response6_caches[
|
|
604
|
+
@response6_caches[domain] = [data, now, ip, true]
|
|
644
605
|
end
|
|
645
606
|
end
|
|
646
607
|
end
|
|
647
|
-
when @h_traffic
|
|
648
|
-
return if data.bytesize < 9
|
|
649
|
-
src_id = data[ 1, 8 ].unpack( 'Q>' ).first
|
|
650
|
-
data = data[ 9..-1 ]
|
|
651
|
-
# puts "got h_traffic #{ src_id } #{ data.bytesize }" if @is_debug
|
|
652
|
-
src, _ = @src_infos.find{ | _, info | info[ :src_id ] == src_id }
|
|
653
|
-
add_src_wbuff( src, data )
|
|
654
|
-
when @h_dst_overflow then
|
|
608
|
+
when @h_traffic
|
|
655
609
|
return if data.bytesize < 9
|
|
656
|
-
src_id = data[
|
|
657
|
-
|
|
658
|
-
src, _ = @src_infos.find{
|
|
659
|
-
|
|
660
|
-
proxy_info[ :paused_srcs ].delete( src )
|
|
661
|
-
when @h_dst_underhalf then
|
|
662
|
-
return if data.bytesize < 9
|
|
663
|
-
src_id = data[ 1, 8 ].unpack( 'Q>' ).first
|
|
664
|
-
puts "got h_dst_underhalf #{ src_id }"
|
|
665
|
-
src, _ = @src_infos.find{ | _, info | info[ :src_id ] == src_id }
|
|
666
|
-
add_read( src )
|
|
610
|
+
src_id = data[1, 8].unpack('Q>').first
|
|
611
|
+
data = data[9..-1]
|
|
612
|
+
src, _ = @src_infos.find{|_, info| info[:src_id] == src_id}
|
|
613
|
+
add_src_wbuff(src, data)
|
|
667
614
|
end
|
|
668
615
|
end
|
|
669
616
|
|
|
670
|
-
def decode_to_msgs(
|
|
617
|
+
def decode_to_msgs(data)
|
|
671
618
|
msgs = []
|
|
672
619
|
part = ''
|
|
673
620
|
|
|
674
621
|
loop do
|
|
675
|
-
if data.bytesize <= 2
|
|
622
|
+
if data.bytesize <= 2
|
|
676
623
|
part = data
|
|
677
624
|
break
|
|
678
625
|
end
|
|
679
626
|
|
|
680
|
-
len = data[
|
|
627
|
+
len = data[0, 2].unpack('n').first
|
|
681
628
|
|
|
682
|
-
if len == 0
|
|
629
|
+
if len == 0
|
|
683
630
|
puts "msg zero len?"
|
|
684
631
|
break
|
|
685
632
|
end
|
|
686
633
|
|
|
687
|
-
if data.bytesize < (
|
|
634
|
+
if data.bytesize < (2 + len)
|
|
688
635
|
part = data
|
|
689
636
|
break
|
|
690
637
|
end
|
|
691
638
|
|
|
692
|
-
msgs << data[
|
|
693
|
-
data = data[
|
|
639
|
+
msgs << data[2, len]
|
|
640
|
+
data = data[(2 + len)..-1]
|
|
694
641
|
break if data.empty?
|
|
695
642
|
end
|
|
696
643
|
|
|
697
|
-
[
|
|
644
|
+
[msgs, part]
|
|
698
645
|
end
|
|
699
646
|
|
|
700
647
|
def loop_heartbeat
|
|
701
648
|
Thread.new do
|
|
702
649
|
loop do
|
|
703
650
|
sleep HEARTBEAT_INTERVAL
|
|
704
|
-
msg = {
|
|
705
|
-
send_data(
|
|
651
|
+
msg = {message_type: 'heartbeat'}
|
|
652
|
+
send_data(@info, JSON.generate(msg), @infod_addr)
|
|
706
653
|
end
|
|
707
654
|
end
|
|
708
655
|
end
|
|
709
656
|
|
|
710
|
-
def make_tunnel(
|
|
657
|
+
def make_tunnel(ip, src)
|
|
711
658
|
return if src.nil? || src.closed?
|
|
712
|
-
src_info = @src_infos[
|
|
713
|
-
domain = src_info[
|
|
714
|
-
port = src_info[
|
|
659
|
+
src_info = @src_infos[src]
|
|
660
|
+
domain = src_info[:destination_domain]
|
|
661
|
+
port = src_info[:destination_port]
|
|
715
662
|
|
|
716
|
-
if @local_ips.include?(
|
|
717
|
-
puts "ignore #{
|
|
718
|
-
close_src(
|
|
663
|
+
if @local_ips.include?(ip) && [@redir_port, @tspd_port].include?(port)
|
|
664
|
+
puts "ignore #{ip}:#{port}"
|
|
665
|
+
close_src(src)
|
|
719
666
|
return
|
|
720
667
|
end
|
|
721
668
|
|
|
722
|
-
if [
|
|
669
|
+
if [domain, ip].include?(@proxyd_host) && ![80, 443].include?(port)
|
|
723
670
|
# 访问远端非http端口,直连
|
|
724
|
-
puts "direct #{
|
|
725
|
-
new_a_dst(
|
|
671
|
+
puts "direct #{ip} #{port}"
|
|
672
|
+
new_a_dst(ip, src)
|
|
726
673
|
return
|
|
727
674
|
end
|
|
728
675
|
|
|
729
|
-
if @is_direct_caches.include?(
|
|
730
|
-
is_direct = @is_direct_caches[
|
|
676
|
+
if @is_direct_caches.include?(ip)
|
|
677
|
+
is_direct = @is_direct_caches[ip]
|
|
731
678
|
else
|
|
732
679
|
begin
|
|
733
|
-
is_direct = @directs.any?{
|
|
680
|
+
is_direct = @directs.any?{|direct| direct.include?(ip)}
|
|
734
681
|
rescue IPAddr::InvalidAddressError => e
|
|
735
|
-
puts "make tunnel #{
|
|
736
|
-
close_src(
|
|
682
|
+
puts "make tunnel #{e.class}"
|
|
683
|
+
close_src(src)
|
|
737
684
|
return
|
|
738
685
|
end
|
|
739
686
|
|
|
740
|
-
@is_direct_caches[
|
|
687
|
+
@is_direct_caches[ip] = is_direct
|
|
741
688
|
end
|
|
742
689
|
|
|
743
|
-
if is_direct
|
|
744
|
-
new_a_dst(
|
|
690
|
+
if is_direct
|
|
691
|
+
new_a_dst(ip, src)
|
|
692
|
+
else
|
|
693
|
+
set_remote(src)
|
|
694
|
+
end
|
|
695
|
+
end
|
|
696
|
+
|
|
697
|
+
def new_a_big
|
|
698
|
+
big = Socket.new(Socket::AF_INET, Socket::SOCK_STREAM, 0)
|
|
699
|
+
big.setsockopt(Socket::IPPROTO_TCP, Socket::TCP_NODELAY, 1)
|
|
700
|
+
|
|
701
|
+
if @is_client_fastopen
|
|
702
|
+
big.setsockopt(Socket::IPPROTO_TCP, Socket::TCP_FASTOPEN, 5)
|
|
745
703
|
else
|
|
746
|
-
|
|
704
|
+
begin
|
|
705
|
+
big.connect_nonblock(@bigd_addr)
|
|
706
|
+
rescue IO::WaitWritable
|
|
707
|
+
rescue Exception => e
|
|
708
|
+
puts "connect bigd #{e.class}"
|
|
709
|
+
big.close
|
|
710
|
+
return
|
|
711
|
+
end
|
|
747
712
|
end
|
|
713
|
+
|
|
714
|
+
puts "big im #{@im}"
|
|
715
|
+
chars = []
|
|
716
|
+
@head_len.times{chars << rand(256)}
|
|
717
|
+
head = "#{chars.pack('C*')}#{[@im.bytesize].pack('C')}#{@im}"
|
|
718
|
+
@big = big
|
|
719
|
+
@big_infos[big] = {
|
|
720
|
+
is_syn: @is_client_fastopen,
|
|
721
|
+
overflowing: false,
|
|
722
|
+
rbuff: '',
|
|
723
|
+
recv_at: Time.new,
|
|
724
|
+
wbuff: head
|
|
725
|
+
}
|
|
726
|
+
add_read(big, :big)
|
|
727
|
+
add_write(big)
|
|
748
728
|
end
|
|
749
729
|
|
|
750
|
-
def new_a_dst(
|
|
730
|
+
def new_a_dst(ip, src)
|
|
751
731
|
return if src.nil? || src.closed?
|
|
752
|
-
src_info = @src_infos[
|
|
753
|
-
domain = src_info[
|
|
754
|
-
port = src_info[
|
|
732
|
+
src_info = @src_infos[src]
|
|
733
|
+
domain = src_info[:destination_domain]
|
|
734
|
+
port = src_info[:destination_port]
|
|
755
735
|
check_expire_dsts
|
|
756
736
|
|
|
757
737
|
begin
|
|
758
|
-
destination_addr = Socket.sockaddr_in(
|
|
759
|
-
dst = Socket.new(
|
|
738
|
+
destination_addr = Socket.sockaddr_in(port, ip)
|
|
739
|
+
dst = Socket.new(Socket::AF_INET, Socket::SOCK_STREAM, 0)
|
|
760
740
|
rescue Exception => e
|
|
761
|
-
puts "new a dst #{
|
|
762
|
-
close_src(
|
|
741
|
+
puts "new a dst #{e.class} #{domain} #{ip}:#{port}"
|
|
742
|
+
close_src(src)
|
|
763
743
|
return
|
|
764
744
|
end
|
|
765
745
|
|
|
766
|
-
dst.setsockopt(
|
|
746
|
+
dst.setsockopt(Socket::IPPROTO_TCP, Socket::TCP_NODELAY, 1)
|
|
767
747
|
|
|
768
748
|
begin
|
|
769
|
-
dst.connect_nonblock(
|
|
749
|
+
dst.connect_nonblock(destination_addr)
|
|
770
750
|
rescue IO::WaitWritable
|
|
771
751
|
rescue Exception => e
|
|
772
|
-
puts "dst connect destination #{
|
|
752
|
+
puts "dst connect destination #{e.class} #{domain} #{ip}:#{port}"
|
|
773
753
|
dst.close
|
|
774
|
-
close_src(
|
|
754
|
+
close_src(src)
|
|
775
755
|
return
|
|
776
756
|
end
|
|
777
757
|
|
|
778
|
-
|
|
758
|
+
@dst_infos[dst] = {
|
|
779
759
|
closing: false,
|
|
780
760
|
connected: false,
|
|
781
761
|
domain: domain,
|
|
@@ -785,404 +765,351 @@ module Girl
|
|
|
785
765
|
src: src,
|
|
786
766
|
wbuff: ''
|
|
787
767
|
}
|
|
768
|
+
src_info[:proxy_type] = :direct
|
|
769
|
+
src_info[:dst] = dst
|
|
788
770
|
|
|
789
|
-
|
|
790
|
-
|
|
791
|
-
src_info[ :dst ] = dst
|
|
792
|
-
|
|
793
|
-
if src_info[ :proxy_proto ] == :http then
|
|
794
|
-
if src_info[ :is_connect ] then
|
|
771
|
+
if src_info[:proxy_proto] == :http
|
|
772
|
+
if src_info[:is_connect]
|
|
795
773
|
puts "add HTTP_OK" if @is_debug
|
|
796
|
-
add_src_wbuff(
|
|
774
|
+
add_src_wbuff(src, HTTP_OK)
|
|
797
775
|
end
|
|
798
|
-
elsif src_info[
|
|
776
|
+
elsif src_info[:proxy_proto] == :socks5
|
|
799
777
|
puts "add_socks5_conn_reply" if @is_debug
|
|
800
|
-
add_socks5_conn_reply(
|
|
778
|
+
add_socks5_conn_reply(src)
|
|
801
779
|
end
|
|
802
780
|
|
|
803
|
-
add_read(
|
|
804
|
-
add_write(
|
|
805
|
-
data = src_info[
|
|
781
|
+
add_read(dst, :dst)
|
|
782
|
+
add_write(dst)
|
|
783
|
+
data = src_info[:rbuff].dup
|
|
806
784
|
|
|
807
|
-
unless data.empty?
|
|
808
|
-
puts "move src rbuff to dst #{
|
|
809
|
-
add_dst_wbuff(
|
|
785
|
+
unless data.empty?
|
|
786
|
+
puts "move src rbuff to dst #{domain} #{data.bytesize}" if @is_debug
|
|
787
|
+
add_dst_wbuff(dst, data)
|
|
810
788
|
end
|
|
811
789
|
end
|
|
812
790
|
|
|
813
|
-
def
|
|
814
|
-
return if relay.nil? || relay.closed?
|
|
815
|
-
check_expire_girls
|
|
816
|
-
|
|
817
|
-
begin
|
|
818
|
-
girl = Socket.new( Socket::AF_INET, Socket::SOCK_STREAM, 0 )
|
|
819
|
-
rescue Exception => e
|
|
820
|
-
puts "new a girl #{ e.class }"
|
|
821
|
-
close_girl( girl )
|
|
822
|
-
return
|
|
823
|
-
end
|
|
824
|
-
|
|
825
|
-
girl.setsockopt( Socket::IPPROTO_TCP, Socket::TCP_NODELAY, 1 )
|
|
826
|
-
|
|
827
|
-
begin
|
|
828
|
-
girl.connect_nonblock( @proxyd_addr )
|
|
829
|
-
rescue IO::WaitWritable
|
|
830
|
-
rescue Exception => e
|
|
831
|
-
puts "girl connect proxyd #{ e.class }"
|
|
832
|
-
girl.close
|
|
833
|
-
close_girl( girl )
|
|
834
|
-
return
|
|
835
|
-
end
|
|
836
|
-
|
|
837
|
-
girl_info = {
|
|
838
|
-
closing: false,
|
|
839
|
-
connected: false,
|
|
840
|
-
is_syn: @is_client_fastopen,
|
|
841
|
-
overflowing: false,
|
|
842
|
-
relay: relay,
|
|
843
|
-
wbuff: ''
|
|
844
|
-
}
|
|
845
|
-
|
|
846
|
-
@girl_infos[ girl ] = girl_info
|
|
847
|
-
add_read( girl, :girl )
|
|
848
|
-
add_write( girl )
|
|
849
|
-
girl
|
|
850
|
-
end
|
|
851
|
-
|
|
852
|
-
def new_a_infod( infod_port )
|
|
791
|
+
def new_a_infod(infod_port)
|
|
853
792
|
infod_host = '127.0.0.1'
|
|
854
|
-
infod_addr = Socket.sockaddr_in(
|
|
855
|
-
infod = Socket.new(
|
|
856
|
-
infod.setsockopt(
|
|
857
|
-
infod.bind(
|
|
858
|
-
puts "infod bind on #{
|
|
859
|
-
add_read(
|
|
860
|
-
info = Socket.new(
|
|
793
|
+
infod_addr = Socket.sockaddr_in(infod_port, infod_host)
|
|
794
|
+
infod = Socket.new(Socket::AF_INET, Socket::SOCK_DGRAM, 0)
|
|
795
|
+
infod.setsockopt(Socket::SOL_SOCKET, Socket::SO_REUSEPORT, 1) if RUBY_PLATFORM.include?('linux')
|
|
796
|
+
infod.bind(infod_addr)
|
|
797
|
+
puts "infod bind on #{infod_host} #{infod_port}"
|
|
798
|
+
add_read(infod, :infod)
|
|
799
|
+
info = Socket.new(Socket::AF_INET, Socket::SOCK_DGRAM, 0)
|
|
861
800
|
@infod_addr = infod_addr
|
|
862
801
|
@infod = infod
|
|
863
802
|
@info = info
|
|
864
803
|
end
|
|
865
804
|
|
|
866
|
-
def new_a_memd(
|
|
805
|
+
def new_a_memd(memd_port)
|
|
867
806
|
memd_host = '127.0.0.1'
|
|
868
|
-
memd = Socket.new(
|
|
869
|
-
memd.setsockopt(
|
|
870
|
-
memd.setsockopt(
|
|
871
|
-
memd.setsockopt(
|
|
872
|
-
memd.bind(
|
|
873
|
-
memd.listen(
|
|
874
|
-
puts "memd listen on #{
|
|
875
|
-
add_read(
|
|
807
|
+
memd = Socket.new(Socket::AF_INET, Socket::SOCK_STREAM, 0)
|
|
808
|
+
memd.setsockopt(Socket::IPPROTO_TCP, Socket::TCP_NODELAY, 1)
|
|
809
|
+
memd.setsockopt(Socket::SOL_SOCKET, Socket::SO_REUSEPORT, 1) if RUBY_PLATFORM.include?('linux')
|
|
810
|
+
memd.setsockopt(Socket::IPPROTO_TCP, Socket::TCP_FASTOPEN, 5) if @is_server_fastopen
|
|
811
|
+
memd.bind(Socket.sockaddr_in(memd_port, memd_host))
|
|
812
|
+
memd.listen(5)
|
|
813
|
+
puts "memd listen on #{memd_host} #{memd_port}"
|
|
814
|
+
add_read(memd, :memd)
|
|
876
815
|
end
|
|
877
816
|
|
|
878
|
-
def new_a_p1(
|
|
817
|
+
def new_a_p1(p2_id)
|
|
879
818
|
check_expire_p1s
|
|
880
819
|
|
|
881
820
|
begin
|
|
882
|
-
p1 = Socket.new(
|
|
821
|
+
p1 = Socket.new(Socket::AF_INET, Socket::SOCK_STREAM, 0)
|
|
883
822
|
rescue Exception => e
|
|
884
|
-
puts "new a p1 #{
|
|
823
|
+
puts "new a p1 #{e.class} #{p2_id}"
|
|
885
824
|
return
|
|
886
825
|
end
|
|
887
826
|
|
|
888
|
-
p1.setsockopt(
|
|
827
|
+
p1.setsockopt(Socket::IPPROTO_TCP, Socket::TCP_NODELAY, 1)
|
|
889
828
|
|
|
890
829
|
begin
|
|
891
|
-
p1.connect_nonblock(
|
|
830
|
+
p1.connect_nonblock(@appd_addr)
|
|
892
831
|
rescue IO::WaitWritable
|
|
893
832
|
rescue Exception => e
|
|
894
|
-
puts "connect appd_addr #{
|
|
833
|
+
puts "connect appd_addr #{e.class} #{p2_id}"
|
|
895
834
|
p1.close
|
|
896
835
|
return
|
|
897
836
|
end
|
|
898
837
|
|
|
899
|
-
|
|
838
|
+
@p1_infos[p1] = {
|
|
900
839
|
closing: false,
|
|
901
840
|
connected: false,
|
|
841
|
+
in: 0,
|
|
842
|
+
is_big: false,
|
|
902
843
|
overflowing: false,
|
|
903
844
|
p2_id: p2_id,
|
|
904
845
|
wbuff: ''
|
|
905
846
|
}
|
|
906
|
-
|
|
907
|
-
|
|
908
|
-
add_read( p1, :p1 )
|
|
909
|
-
add_write( p1 )
|
|
847
|
+
add_read(p1, :p1)
|
|
848
|
+
add_write(p1)
|
|
910
849
|
end
|
|
911
850
|
|
|
912
851
|
def new_a_proxy
|
|
913
|
-
proxy = Socket.new(
|
|
914
|
-
proxy.setsockopt(
|
|
852
|
+
proxy = Socket.new(Socket::AF_INET, Socket::SOCK_STREAM, 0)
|
|
853
|
+
proxy.setsockopt(Socket::IPPROTO_TCP, Socket::TCP_NODELAY, 1)
|
|
915
854
|
|
|
916
|
-
if @is_client_fastopen
|
|
917
|
-
proxy.setsockopt(
|
|
855
|
+
if @is_client_fastopen
|
|
856
|
+
proxy.setsockopt(Socket::IPPROTO_TCP, Socket::TCP_FASTOPEN, 5)
|
|
918
857
|
else
|
|
919
858
|
begin
|
|
920
|
-
proxy.connect_nonblock(
|
|
859
|
+
proxy.connect_nonblock(@proxyd_addr)
|
|
921
860
|
rescue IO::WaitWritable
|
|
922
861
|
rescue Exception => e
|
|
923
|
-
puts "connect proxyd #{
|
|
862
|
+
puts "connect proxyd #{e.class}"
|
|
924
863
|
proxy.close
|
|
925
864
|
return
|
|
926
865
|
end
|
|
927
866
|
end
|
|
928
867
|
|
|
929
|
-
puts "im #{
|
|
868
|
+
puts "proxy im #{@im}"
|
|
930
869
|
chars = []
|
|
931
|
-
@head_len.times{
|
|
932
|
-
head = "#{
|
|
933
|
-
|
|
934
|
-
|
|
870
|
+
@head_len.times{chars << rand(256)}
|
|
871
|
+
head = "#{chars.pack('C*')}#{[@im.bytesize].pack('C')}#{@im}"
|
|
872
|
+
@proxy = proxy
|
|
873
|
+
@proxy_infos[proxy] = {
|
|
935
874
|
is_syn: @is_client_fastopen,
|
|
936
|
-
paused_p1s: [],
|
|
937
|
-
paused_srcs: [],
|
|
938
875
|
rbuff: '',
|
|
939
|
-
recv_at:
|
|
876
|
+
recv_at: Time.new,
|
|
940
877
|
wbuff: head
|
|
941
878
|
}
|
|
942
|
-
|
|
943
|
-
|
|
944
|
-
|
|
945
|
-
|
|
946
|
-
|
|
947
|
-
|
|
948
|
-
|
|
949
|
-
|
|
950
|
-
|
|
951
|
-
redir
|
|
952
|
-
redir.
|
|
953
|
-
redir.
|
|
954
|
-
redir
|
|
955
|
-
redir
|
|
956
|
-
redir.bind( Socket.sockaddr_in( redir_port, redir_host ) )
|
|
957
|
-
redir.listen( BACKLOG )
|
|
958
|
-
puts "redir listen on #{ redir_host } #{ redir_port }"
|
|
959
|
-
add_read( redir, :redir )
|
|
879
|
+
add_read(proxy, :proxy)
|
|
880
|
+
add_write(proxy)
|
|
881
|
+
end
|
|
882
|
+
|
|
883
|
+
def new_a_redir(redir_host, redir_port)
|
|
884
|
+
redir = Socket.new(Socket::AF_INET, Socket::SOCK_STREAM, 0)
|
|
885
|
+
redir.setsockopt(Socket::IPPROTO_TCP, Socket::TCP_NODELAY, 1)
|
|
886
|
+
redir.setsockopt(Socket::SOL_SOCKET, Socket::SO_REUSEADDR, 1)
|
|
887
|
+
redir.setsockopt(Socket::SOL_SOCKET, Socket::SO_REUSEPORT, 1) if RUBY_PLATFORM.include?('linux')
|
|
888
|
+
redir.setsockopt(Socket::IPPROTO_TCP, Socket::TCP_FASTOPEN, BACKLOG) if @is_server_fastopen
|
|
889
|
+
redir.bind(Socket.sockaddr_in(redir_port, redir_host))
|
|
890
|
+
redir.listen(BACKLOG)
|
|
891
|
+
puts "redir listen on #{redir_host} #{redir_port}"
|
|
892
|
+
add_read(redir, :redir)
|
|
960
893
|
@redir_port = redir_port
|
|
961
894
|
@redir_local_address = redir.local_address
|
|
962
895
|
end
|
|
963
896
|
|
|
964
|
-
def
|
|
965
|
-
relayd = Socket.new( Socket::AF_INET, Socket::SOCK_STREAM, 0 )
|
|
966
|
-
relayd.setsockopt( Socket::IPPROTO_TCP, Socket::TCP_NODELAY, 1 )
|
|
967
|
-
relayd.setsockopt( Socket::SOL_SOCKET, Socket::SO_REUSEADDR, 1 )
|
|
968
|
-
relayd.setsockopt( Socket::SOL_SOCKET, Socket::SO_REUSEPORT, 1 ) if RUBY_PLATFORM.include?( 'linux' )
|
|
969
|
-
relayd.setsockopt( Socket::IPPROTO_TCP, Socket::TCP_FASTOPEN, BACKLOG ) if @is_server_fastopen
|
|
970
|
-
relayd.bind( Socket.sockaddr_in( relayd_port, relayd_host ) )
|
|
971
|
-
relayd.listen( BACKLOG )
|
|
972
|
-
puts "relayd listen on #{ relayd_host } #{ relayd_port }"
|
|
973
|
-
add_read( relayd, :relayd )
|
|
974
|
-
@relayd_port = relayd_port
|
|
975
|
-
end
|
|
976
|
-
|
|
977
|
-
def new_a_rsv( data, addrinfo, domain, type )
|
|
897
|
+
def new_a_rsv(data, addrinfo, domain, type)
|
|
978
898
|
check_expire_rsvs
|
|
979
|
-
rsv = Socket.new(
|
|
899
|
+
rsv = Socket.new(Socket::AF_INET, Socket::SOCK_DGRAM, 0)
|
|
980
900
|
|
|
981
901
|
begin
|
|
982
|
-
@nameserver_addrs.each{
|
|
902
|
+
@nameserver_addrs.each{|addr| rsv.sendmsg(data, 0, addr)}
|
|
983
903
|
rescue Exception => e
|
|
984
|
-
puts "rsv send data #{
|
|
904
|
+
puts "rsv send data #{e.class}"
|
|
985
905
|
rsv.close
|
|
986
906
|
return
|
|
987
907
|
end
|
|
988
908
|
|
|
989
|
-
|
|
909
|
+
@rsv_infos[rsv] = {
|
|
990
910
|
addrinfo: addrinfo,
|
|
991
911
|
domain: domain,
|
|
992
912
|
type: type
|
|
993
913
|
}
|
|
994
|
-
|
|
995
|
-
@rsv_infos[ rsv ] = rsv_info
|
|
996
|
-
add_read( rsv, :rsv )
|
|
914
|
+
add_read(rsv, :rsv)
|
|
997
915
|
end
|
|
998
916
|
|
|
999
|
-
def new_a_rsvd(
|
|
1000
|
-
rsvd_addr = Socket.sockaddr_in(
|
|
1001
|
-
rsvd = Socket.new(
|
|
1002
|
-
rsvd.setsockopt(
|
|
1003
|
-
rsvd.bind(
|
|
1004
|
-
puts "rsvd bind on #{
|
|
1005
|
-
add_read(
|
|
917
|
+
def new_a_rsvd(rsvd_host, rsvd_port)
|
|
918
|
+
rsvd_addr = Socket.sockaddr_in(rsvd_port, rsvd_host)
|
|
919
|
+
rsvd = Socket.new(Socket::AF_INET, Socket::SOCK_DGRAM, 0)
|
|
920
|
+
rsvd.setsockopt(Socket::SOL_SOCKET, Socket::SO_REUSEPORT, 1) if RUBY_PLATFORM.include?('linux')
|
|
921
|
+
rsvd.bind(rsvd_addr)
|
|
922
|
+
puts "rsvd bind on #{rsvd_host} #{rsvd_port}"
|
|
923
|
+
add_read(rsvd, :rsvd)
|
|
1006
924
|
@rsvd = rsvd
|
|
1007
925
|
end
|
|
1008
926
|
|
|
1009
|
-
def new_a_tspd(
|
|
1010
|
-
tspd = Socket.new(
|
|
1011
|
-
tspd.setsockopt(
|
|
1012
|
-
tspd.setsockopt(
|
|
1013
|
-
tspd.setsockopt(
|
|
1014
|
-
tspd.setsockopt(
|
|
1015
|
-
tspd.bind(
|
|
1016
|
-
tspd.listen(
|
|
1017
|
-
puts "tspd listen on #{
|
|
1018
|
-
add_read(
|
|
927
|
+
def new_a_tspd(tspd_host, tspd_port)
|
|
928
|
+
tspd = Socket.new(Socket::AF_INET, Socket::SOCK_STREAM, 0)
|
|
929
|
+
tspd.setsockopt(Socket::IPPROTO_TCP, Socket::TCP_NODELAY, 1)
|
|
930
|
+
tspd.setsockopt(Socket::SOL_SOCKET, Socket::SO_REUSEADDR, 1)
|
|
931
|
+
tspd.setsockopt(Socket::SOL_SOCKET, Socket::SO_REUSEPORT, 1) if RUBY_PLATFORM.include?('linux')
|
|
932
|
+
tspd.setsockopt(Socket::IPPROTO_TCP, Socket::TCP_FASTOPEN, BACKLOG) if @is_server_fastopen
|
|
933
|
+
tspd.bind(Socket.sockaddr_in(tspd_port, tspd_host))
|
|
934
|
+
tspd.listen(BACKLOG)
|
|
935
|
+
puts "tspd listen on #{tspd_host} #{tspd_port}"
|
|
936
|
+
add_read(tspd, :tspd)
|
|
1019
937
|
@tspd_port = tspd_port
|
|
1020
938
|
end
|
|
1021
939
|
|
|
1022
|
-
def pack_a_chunk(
|
|
1023
|
-
"#{
|
|
940
|
+
def pack_a_chunk(msg)
|
|
941
|
+
"#{[msg.bytesize].pack('n')}#{msg}"
|
|
1024
942
|
end
|
|
1025
943
|
|
|
1026
|
-
def pack_p2_traffic(
|
|
944
|
+
def pack_p2_traffic(p2_id, data)
|
|
1027
945
|
chunks = ''
|
|
1028
946
|
|
|
1029
947
|
loop do
|
|
1030
|
-
part = data[
|
|
1031
|
-
|
|
1032
|
-
|
|
1033
|
-
|
|
1034
|
-
data = data[ part.bytesize..-1 ]
|
|
948
|
+
part = data[0, 65526]
|
|
949
|
+
msg = "#{@h_p2_traffic}#{[p2_id].pack('Q>')}#{part}"
|
|
950
|
+
chunks << pack_a_chunk(msg)
|
|
951
|
+
data = data[part.bytesize..-1]
|
|
1035
952
|
break if data.empty?
|
|
1036
953
|
end
|
|
1037
954
|
|
|
1038
955
|
chunks
|
|
1039
956
|
end
|
|
1040
957
|
|
|
1041
|
-
def pack_traffic(
|
|
958
|
+
def pack_traffic(src_id, data)
|
|
1042
959
|
chunks = ''
|
|
1043
960
|
|
|
1044
961
|
loop do
|
|
1045
|
-
part = data[
|
|
1046
|
-
|
|
1047
|
-
|
|
1048
|
-
|
|
1049
|
-
data = data[ part.bytesize..-1 ]
|
|
962
|
+
part = data[0, 65526]
|
|
963
|
+
msg = "#{@h_traffic}#{[src_id].pack('Q>')}#{part}"
|
|
964
|
+
chunks << pack_a_chunk(msg)
|
|
965
|
+
data = data[part.bytesize..-1]
|
|
1050
966
|
break if data.empty?
|
|
1051
967
|
end
|
|
1052
968
|
|
|
1053
969
|
chunks
|
|
1054
970
|
end
|
|
1055
971
|
|
|
1056
|
-
def
|
|
972
|
+
def read_big(big)
|
|
1057
973
|
begin
|
|
1058
|
-
data
|
|
974
|
+
data = big.read_nonblock(READ_SIZE)
|
|
975
|
+
rescue Errno::ENOTCONN => e
|
|
976
|
+
return
|
|
1059
977
|
rescue Exception => e
|
|
1060
|
-
puts "
|
|
1061
|
-
|
|
978
|
+
puts "read big #{e.class}" if @is_debug
|
|
979
|
+
close_big(big)
|
|
1062
980
|
return
|
|
1063
981
|
end
|
|
1064
982
|
|
|
1065
|
-
|
|
983
|
+
set_update(big)
|
|
984
|
+
big_info = @big_infos[big]
|
|
985
|
+
data = "#{big_info[:rbuff]}#{data}"
|
|
986
|
+
msgs, part = decode_to_msgs(data)
|
|
987
|
+
msgs.each{|msg| deal_big_msg(msg)}
|
|
988
|
+
big_info[:rbuff] = part
|
|
989
|
+
end
|
|
1066
990
|
|
|
991
|
+
def read_dns(dns)
|
|
1067
992
|
begin
|
|
1068
|
-
|
|
993
|
+
data, addrinfo, rflags, *controls = dns.recvmsg
|
|
1069
994
|
rescue Exception => e
|
|
1070
|
-
puts "dns
|
|
1071
|
-
close_dns(
|
|
995
|
+
puts "dns recvmsg #{e.class}"
|
|
996
|
+
close_dns(dns)
|
|
1072
997
|
return
|
|
1073
998
|
end
|
|
1074
999
|
|
|
1075
|
-
|
|
1076
|
-
domain = dns_info[ :domain ]
|
|
1077
|
-
|
|
1078
|
-
if ip then
|
|
1079
|
-
src = dns_info[ :src ]
|
|
1080
|
-
make_tunnel( ip, src )
|
|
1081
|
-
puts "set resolv cache #{ domain } #{ ip }" if @is_debug
|
|
1082
|
-
@resolv_caches[ domain ] = [ ip, Time.new ]
|
|
1083
|
-
else
|
|
1084
|
-
puts "no ip in answer #{ domain }"
|
|
1085
|
-
close_src( src )
|
|
1086
|
-
end
|
|
1087
|
-
|
|
1088
|
-
close_dns( dns )
|
|
1089
|
-
end
|
|
1000
|
+
return if data.empty?
|
|
1090
1001
|
|
|
1091
|
-
def read_dst( dst )
|
|
1092
1002
|
begin
|
|
1093
|
-
|
|
1094
|
-
rescue Errno::ENOTCONN => e
|
|
1095
|
-
return
|
|
1003
|
+
ip = seek_ip(data)
|
|
1096
1004
|
rescue Exception => e
|
|
1097
|
-
|
|
1005
|
+
puts "dns seek ip #{e.class} #{e.message}"
|
|
1006
|
+
close_dns(dns)
|
|
1098
1007
|
return
|
|
1099
1008
|
end
|
|
1100
1009
|
|
|
1101
|
-
|
|
1102
|
-
|
|
1103
|
-
|
|
1104
|
-
|
|
1105
|
-
|
|
1010
|
+
dns_info = @dns_infos[dns]
|
|
1011
|
+
domain = dns_info[:domain]
|
|
1012
|
+
|
|
1013
|
+
if ip
|
|
1014
|
+
src = dns_info[:src]
|
|
1015
|
+
make_tunnel(ip, src)
|
|
1016
|
+
puts "set resolv cache #{domain} #{ip}" if @is_debug
|
|
1017
|
+
@resolv_caches[domain] = [ip, Time.new]
|
|
1018
|
+
else
|
|
1019
|
+
puts "no ip in answer #{domain}"
|
|
1020
|
+
close_src(src)
|
|
1021
|
+
end
|
|
1022
|
+
|
|
1023
|
+
close_dns(dns)
|
|
1106
1024
|
end
|
|
1107
1025
|
|
|
1108
|
-
def
|
|
1026
|
+
def read_dst(dst)
|
|
1109
1027
|
begin
|
|
1110
|
-
data =
|
|
1028
|
+
data = dst.read_nonblock(READ_SIZE)
|
|
1111
1029
|
rescue Errno::ENOTCONN => e
|
|
1112
1030
|
return
|
|
1113
1031
|
rescue Exception => e
|
|
1114
|
-
|
|
1032
|
+
puts "read dst #{e.class}" if @is_debug
|
|
1033
|
+
close_dst(dst)
|
|
1115
1034
|
return
|
|
1116
1035
|
end
|
|
1117
1036
|
|
|
1118
|
-
set_update(
|
|
1119
|
-
|
|
1120
|
-
|
|
1121
|
-
|
|
1037
|
+
set_update(dst)
|
|
1038
|
+
dst_info = @dst_infos[dst]
|
|
1039
|
+
src = dst_info[:src]
|
|
1040
|
+
add_src_wbuff(src, data)
|
|
1122
1041
|
end
|
|
1123
1042
|
|
|
1124
|
-
def read_infod(
|
|
1043
|
+
def read_infod(infod)
|
|
1125
1044
|
begin
|
|
1126
1045
|
data, addrinfo, rflags, *controls = infod.recvmsg
|
|
1127
1046
|
rescue Exception => e
|
|
1128
|
-
puts "infod recvmsg #{
|
|
1047
|
+
puts "infod recvmsg #{e.class}"
|
|
1129
1048
|
return
|
|
1130
1049
|
end
|
|
1131
1050
|
|
|
1132
1051
|
return if data.empty?
|
|
1133
1052
|
|
|
1134
1053
|
begin
|
|
1135
|
-
msg = JSON.parse(
|
|
1054
|
+
msg = JSON.parse(data, symbolize_names: true)
|
|
1136
1055
|
rescue JSON::ParserError, EncodingError => e
|
|
1137
|
-
puts "read infod #{
|
|
1056
|
+
puts "read infod #{e.class}"
|
|
1138
1057
|
return
|
|
1139
1058
|
end
|
|
1140
1059
|
|
|
1141
|
-
message_type = msg[
|
|
1060
|
+
message_type = msg[:message_type]
|
|
1142
1061
|
|
|
1143
1062
|
case message_type
|
|
1144
|
-
when 'heartbeat'
|
|
1145
|
-
if @proxy.closed?
|
|
1063
|
+
when 'heartbeat'
|
|
1064
|
+
new_a_proxy if @proxy.closed?
|
|
1065
|
+
new_a_big if @big.closed?
|
|
1066
|
+
proxy_info = @proxy_infos[@proxy]
|
|
1067
|
+
|
|
1068
|
+
if Time.new.to_i - proxy_info[:recv_at].to_i >= @expire_proxy_after
|
|
1069
|
+
puts "renew proxy"
|
|
1070
|
+
close_proxy(@proxy)
|
|
1146
1071
|
new_a_proxy
|
|
1147
1072
|
else
|
|
1148
|
-
|
|
1073
|
+
add_proxy_wbuff(pack_a_chunk(@h_heartbeat))
|
|
1074
|
+
end
|
|
1149
1075
|
|
|
1150
|
-
|
|
1151
|
-
|
|
1152
|
-
|
|
1153
|
-
|
|
1154
|
-
|
|
1155
|
-
|
|
1156
|
-
|
|
1076
|
+
big_info = @big_infos[@big]
|
|
1077
|
+
|
|
1078
|
+
if Time.new.to_i - big_info[:recv_at].to_i >= @expire_proxy_after
|
|
1079
|
+
puts "renew big"
|
|
1080
|
+
close_big(@big)
|
|
1081
|
+
new_a_big
|
|
1082
|
+
else
|
|
1083
|
+
add_big_wbuff(pack_a_chunk(@h_heartbeat))
|
|
1157
1084
|
end
|
|
1158
1085
|
end
|
|
1159
1086
|
end
|
|
1160
1087
|
|
|
1161
|
-
def read_mem(
|
|
1088
|
+
def read_mem(mem)
|
|
1162
1089
|
begin
|
|
1163
|
-
mem.read_nonblock(
|
|
1090
|
+
mem.read_nonblock(READ_SIZE)
|
|
1164
1091
|
rescue Errno::ENOTCONN => e
|
|
1165
1092
|
return
|
|
1166
1093
|
rescue Exception => e
|
|
1167
|
-
close_mem(
|
|
1094
|
+
close_mem(mem)
|
|
1168
1095
|
return
|
|
1169
1096
|
end
|
|
1170
1097
|
|
|
1171
|
-
set_update(
|
|
1098
|
+
set_update(mem)
|
|
1172
1099
|
src_arr = []
|
|
1173
1100
|
|
|
1174
|
-
@src_infos.each do |
|
|
1101
|
+
@src_infos.each do |_, info|
|
|
1175
1102
|
src_arr << {
|
|
1176
|
-
addrinfo: info[
|
|
1177
|
-
destination_domain: info[
|
|
1178
|
-
destination_port: info[
|
|
1103
|
+
addrinfo: info[:addrinfo].ip_unpack,
|
|
1104
|
+
destination_domain: info[:destination_domain],
|
|
1105
|
+
destination_port: info[:destination_port]
|
|
1179
1106
|
}
|
|
1180
1107
|
end
|
|
1181
1108
|
|
|
1182
1109
|
msg = {
|
|
1183
1110
|
resolv_caches: @resolv_caches.sort,
|
|
1184
|
-
response_caches: @response_caches.sort.map{
|
|
1185
|
-
response6_caches: @response6_caches.sort.map{
|
|
1111
|
+
response_caches: @response_caches.sort.map{|a| [a[0], a[1][2], a[1][3]]},
|
|
1112
|
+
response6_caches: @response6_caches.sort.map{|a| [a[0], a[1][2], a[1][3]]},
|
|
1186
1113
|
sizes: {
|
|
1187
1114
|
directs: @directs.size,
|
|
1188
1115
|
remotes: @remotes.size,
|
|
@@ -1191,9 +1118,8 @@ module Girl
|
|
|
1191
1118
|
roles: @roles.size,
|
|
1192
1119
|
updates: @updates.size,
|
|
1193
1120
|
proxy_infos: @proxy_infos.size,
|
|
1121
|
+
big_infos: @big_infos.size,
|
|
1194
1122
|
mem_infos: @mem_infos.size,
|
|
1195
|
-
relay_infos: @relay_infos.size,
|
|
1196
|
-
girl_infos: @girl_infos.size,
|
|
1197
1123
|
src_infos: @src_infos.size,
|
|
1198
1124
|
dst_infos: @dst_infos.size,
|
|
1199
1125
|
dns_infos: @dns_infos.size,
|
|
@@ -1210,16 +1136,16 @@ module Girl
|
|
|
1210
1136
|
src_arr: src_arr
|
|
1211
1137
|
}
|
|
1212
1138
|
|
|
1213
|
-
add_mem_wbuff(
|
|
1139
|
+
add_mem_wbuff(mem, JSON.generate(msg))
|
|
1214
1140
|
end
|
|
1215
1141
|
|
|
1216
|
-
def read_memd(
|
|
1142
|
+
def read_memd(memd)
|
|
1217
1143
|
check_expire_mems
|
|
1218
1144
|
|
|
1219
1145
|
begin
|
|
1220
1146
|
mem, addrinfo = memd.accept_nonblock
|
|
1221
1147
|
rescue Exception => e
|
|
1222
|
-
puts "memd accept #{
|
|
1148
|
+
puts "memd accept #{e.class}"
|
|
1223
1149
|
return
|
|
1224
1150
|
end
|
|
1225
1151
|
|
|
@@ -1227,82 +1153,85 @@ module Girl
|
|
|
1227
1153
|
wbuff: ''
|
|
1228
1154
|
}
|
|
1229
1155
|
|
|
1230
|
-
@mem_infos[
|
|
1231
|
-
add_read(
|
|
1156
|
+
@mem_infos[mem] = mem_info
|
|
1157
|
+
add_read(mem, :mem)
|
|
1232
1158
|
end
|
|
1233
1159
|
|
|
1234
|
-
def read_p1(
|
|
1160
|
+
def read_p1(p1)
|
|
1235
1161
|
begin
|
|
1236
|
-
data = p1.read_nonblock(
|
|
1162
|
+
data = p1.read_nonblock(READ_SIZE)
|
|
1237
1163
|
rescue Errno::ENOTCONN => e
|
|
1238
1164
|
return
|
|
1239
1165
|
rescue Exception => e
|
|
1240
|
-
|
|
1166
|
+
puts "read p1 #{e.class}" if @is_debug
|
|
1167
|
+
close_p1(p1)
|
|
1241
1168
|
return
|
|
1242
1169
|
end
|
|
1243
1170
|
|
|
1244
|
-
set_update(
|
|
1171
|
+
set_update(p1)
|
|
1245
1172
|
|
|
1246
|
-
if @proxy.closed?
|
|
1247
|
-
close_p1(
|
|
1173
|
+
if @proxy.closed?
|
|
1174
|
+
close_p1(p1)
|
|
1248
1175
|
return
|
|
1249
1176
|
end
|
|
1250
1177
|
|
|
1251
|
-
p1_info = @p1_infos[
|
|
1252
|
-
|
|
1253
|
-
|
|
1254
|
-
add_proxy_wbuff( pack_p2_traffic( p2_id, data ) )
|
|
1178
|
+
p1_info = @p1_infos[p1]
|
|
1179
|
+
p1_info[:in] += data.bytesize
|
|
1180
|
+
p2_id = p1_info[:p2_id]
|
|
1255
1181
|
|
|
1256
|
-
|
|
1257
|
-
|
|
1258
|
-
|
|
1182
|
+
if !p1_info[:is_big] && (p1_info[:in] >= READ_SIZE)
|
|
1183
|
+
puts "set p1 is big #{p2_id}"
|
|
1184
|
+
p1_info[:is_big] = true
|
|
1185
|
+
end
|
|
1259
1186
|
|
|
1260
|
-
|
|
1261
|
-
|
|
1262
|
-
|
|
1263
|
-
|
|
1264
|
-
|
|
1187
|
+
data = pack_p2_traffic(p2_id, data)
|
|
1188
|
+
|
|
1189
|
+
if p1_info[:is_big]
|
|
1190
|
+
add_big_wbuff(data)
|
|
1191
|
+
else
|
|
1192
|
+
add_proxy_wbuff(data)
|
|
1265
1193
|
end
|
|
1266
1194
|
end
|
|
1267
1195
|
|
|
1268
|
-
def read_proxy(
|
|
1196
|
+
def read_proxy(proxy)
|
|
1269
1197
|
begin
|
|
1270
|
-
data = proxy.read_nonblock(
|
|
1198
|
+
data = proxy.read_nonblock(READ_SIZE)
|
|
1271
1199
|
rescue Errno::ENOTCONN => e
|
|
1272
1200
|
return
|
|
1273
1201
|
rescue Exception => e
|
|
1274
|
-
|
|
1202
|
+
puts "read proxy #{e.class}" if @is_debug
|
|
1203
|
+
close_proxy(proxy)
|
|
1275
1204
|
return
|
|
1276
1205
|
end
|
|
1277
1206
|
|
|
1278
|
-
set_update(
|
|
1279
|
-
proxy_info = @proxy_infos[
|
|
1280
|
-
data = "#{
|
|
1281
|
-
|
|
1282
|
-
msgs
|
|
1283
|
-
|
|
1284
|
-
proxy_info[ :rbuff ] = part
|
|
1207
|
+
set_update(proxy)
|
|
1208
|
+
proxy_info = @proxy_infos[proxy]
|
|
1209
|
+
data = "#{proxy_info[:rbuff]}#{data}"
|
|
1210
|
+
msgs, part = decode_to_msgs(data)
|
|
1211
|
+
msgs.each{|msg| deal_msg(msg)}
|
|
1212
|
+
proxy_info[:rbuff] = part
|
|
1285
1213
|
end
|
|
1286
1214
|
|
|
1287
|
-
def read_redir(
|
|
1215
|
+
def read_redir(redir)
|
|
1288
1216
|
check_expire_srcs
|
|
1289
1217
|
|
|
1290
1218
|
begin
|
|
1291
1219
|
src, addrinfo = redir.accept_nonblock
|
|
1292
1220
|
rescue IO::WaitReadable, Errno::EINTR => e
|
|
1293
|
-
puts "redir accept #{
|
|
1221
|
+
puts "redir accept #{e.class}"
|
|
1294
1222
|
return
|
|
1295
1223
|
end
|
|
1296
1224
|
|
|
1297
|
-
puts "redir accept a src #{
|
|
1298
|
-
src_id = rand(
|
|
1299
|
-
|
|
1300
|
-
src_info = {
|
|
1225
|
+
puts "redir accept a src #{addrinfo.ip_unpack.inspect}" if @is_debug
|
|
1226
|
+
src_id = rand((2 ** 64) - 2) + 1
|
|
1227
|
+
@src_infos[src] = {
|
|
1301
1228
|
addrinfo: addrinfo,
|
|
1302
1229
|
closing: false,
|
|
1303
1230
|
destination_domain: nil,
|
|
1304
1231
|
destination_port: nil,
|
|
1305
1232
|
dst: nil,
|
|
1233
|
+
in: 0,
|
|
1234
|
+
is_big: false,
|
|
1306
1235
|
is_connect: true,
|
|
1307
1236
|
overflowing: false,
|
|
1308
1237
|
proxy_proto: :uncheck, # :uncheck / :http / :socks5
|
|
@@ -1311,183 +1240,138 @@ module Girl
|
|
|
1311
1240
|
src_id: src_id,
|
|
1312
1241
|
wbuff: ''
|
|
1313
1242
|
}
|
|
1314
|
-
|
|
1315
|
-
@src_infos[ src ] = src_info
|
|
1316
|
-
add_read( src, :src )
|
|
1243
|
+
add_read(src, :src)
|
|
1317
1244
|
end
|
|
1318
1245
|
|
|
1319
|
-
def
|
|
1320
|
-
begin
|
|
1321
|
-
data = relay.read_nonblock( READ_SIZE )
|
|
1322
|
-
rescue Errno::ENOTCONN => e
|
|
1323
|
-
return
|
|
1324
|
-
rescue Exception => e
|
|
1325
|
-
close_relay( relay )
|
|
1326
|
-
return
|
|
1327
|
-
end
|
|
1328
|
-
|
|
1329
|
-
set_update( relay )
|
|
1330
|
-
relay_info = @relay_infos[ relay ]
|
|
1331
|
-
girl = relay_info[ :girl ]
|
|
1332
|
-
add_girl_wbuff( girl, data )
|
|
1333
|
-
end
|
|
1334
|
-
|
|
1335
|
-
def read_relayd( relayd )
|
|
1336
|
-
check_expire_relays
|
|
1337
|
-
|
|
1338
|
-
begin
|
|
1339
|
-
relay, addrinfo = relayd.accept_nonblock
|
|
1340
|
-
rescue IO::WaitReadable, Errno::EINTR => e
|
|
1341
|
-
puts "relayd accept #{ e.class }"
|
|
1342
|
-
return
|
|
1343
|
-
end
|
|
1344
|
-
|
|
1345
|
-
puts "relayd accept a relay #{ addrinfo.ip_unpack.inspect }"
|
|
1346
|
-
|
|
1347
|
-
relay_info = {
|
|
1348
|
-
addrinfo: addrinfo,
|
|
1349
|
-
closing: false,
|
|
1350
|
-
girl: nil,
|
|
1351
|
-
overflowing: false,
|
|
1352
|
-
wbuff: ''
|
|
1353
|
-
}
|
|
1354
|
-
|
|
1355
|
-
@relay_infos[ relay ] = relay_info
|
|
1356
|
-
add_read( relay, :relay )
|
|
1357
|
-
relay_info[ :girl ] = new_a_girl( relay )
|
|
1358
|
-
end
|
|
1359
|
-
|
|
1360
|
-
def read_rsv( rsv )
|
|
1246
|
+
def read_rsv(rsv)
|
|
1361
1247
|
begin
|
|
1362
1248
|
data, addrinfo, rflags, *controls = rsv.recvmsg
|
|
1363
1249
|
rescue Exception => e
|
|
1364
|
-
puts "rsv recvmsg #{
|
|
1365
|
-
close_rsv(
|
|
1250
|
+
puts "rsv recvmsg #{e.class}"
|
|
1251
|
+
close_rsv(rsv)
|
|
1366
1252
|
return
|
|
1367
1253
|
end
|
|
1368
1254
|
|
|
1369
1255
|
return if data.empty?
|
|
1370
1256
|
|
|
1371
|
-
rsv_info = @rsv_infos[
|
|
1372
|
-
addrinfo = rsv_info[
|
|
1373
|
-
domain = rsv_info[
|
|
1374
|
-
type = rsv_info[
|
|
1375
|
-
send_data(
|
|
1257
|
+
rsv_info = @rsv_infos[rsv]
|
|
1258
|
+
addrinfo = rsv_info[:addrinfo]
|
|
1259
|
+
domain = rsv_info[:domain]
|
|
1260
|
+
type = rsv_info[:type]
|
|
1261
|
+
send_data(@rsvd, data, addrinfo)
|
|
1376
1262
|
|
|
1377
1263
|
begin
|
|
1378
|
-
ip = seek_ip(
|
|
1264
|
+
ip = seek_ip(data)
|
|
1379
1265
|
rescue Exception => e
|
|
1380
|
-
puts "rsv seek ip #{
|
|
1381
|
-
close_rsv(
|
|
1266
|
+
puts "rsv seek ip #{e.class} #{e.message}"
|
|
1267
|
+
close_rsv(rsv)
|
|
1382
1268
|
return
|
|
1383
1269
|
end
|
|
1384
1270
|
|
|
1385
|
-
if ip
|
|
1386
|
-
if type == 1
|
|
1387
|
-
puts "set response cache #{
|
|
1388
|
-
@response_caches[
|
|
1271
|
+
if ip
|
|
1272
|
+
if type == 1
|
|
1273
|
+
puts "set response cache #{domain} #{ip}" if @is_debug
|
|
1274
|
+
@response_caches[domain] = [data, Time.new, ip, false]
|
|
1389
1275
|
else
|
|
1390
|
-
puts "set response6 cache #{
|
|
1391
|
-
@response6_caches[
|
|
1276
|
+
puts "set response6 cache #{domain} #{ip}" if @is_debug
|
|
1277
|
+
@response6_caches[domain] = [data, Time.new, ip, false]
|
|
1392
1278
|
end
|
|
1393
1279
|
end
|
|
1394
1280
|
|
|
1395
|
-
close_rsv(
|
|
1281
|
+
close_rsv(rsv)
|
|
1396
1282
|
end
|
|
1397
1283
|
|
|
1398
|
-
def read_rsvd(
|
|
1284
|
+
def read_rsvd(rsvd)
|
|
1399
1285
|
begin
|
|
1400
1286
|
data, addrinfo, rflags, *controls = rsvd.recvmsg
|
|
1401
1287
|
rescue Exception => e
|
|
1402
|
-
puts "rsvd recvmsg #{
|
|
1288
|
+
puts "rsvd recvmsg #{e.class}"
|
|
1403
1289
|
return
|
|
1404
1290
|
end
|
|
1405
1291
|
|
|
1406
1292
|
return if data.empty?
|
|
1407
1293
|
|
|
1408
1294
|
begin
|
|
1409
|
-
id, domain, type = seek_question_dn(
|
|
1295
|
+
id, domain, type = seek_question_dn(data)
|
|
1410
1296
|
rescue Exception => e
|
|
1411
|
-
puts "seek question dn #{
|
|
1297
|
+
puts "seek question dn #{e.class} #{e.message}"
|
|
1412
1298
|
return
|
|
1413
1299
|
end
|
|
1414
1300
|
|
|
1415
|
-
return unless [
|
|
1301
|
+
return unless [1, 12, 28].include?(type)
|
|
1416
1302
|
|
|
1417
|
-
if type == 12
|
|
1418
|
-
new_a_rsv(
|
|
1303
|
+
if type == 12
|
|
1304
|
+
new_a_rsv(data, addrinfo, domain, type)
|
|
1419
1305
|
return
|
|
1420
1306
|
end
|
|
1421
1307
|
|
|
1422
|
-
if type == 1
|
|
1423
|
-
response_cache = @response_caches[
|
|
1308
|
+
if type == 1
|
|
1309
|
+
response_cache = @response_caches[domain]
|
|
1424
1310
|
else
|
|
1425
|
-
response_cache = @response6_caches[
|
|
1311
|
+
response_cache = @response6_caches[domain]
|
|
1426
1312
|
end
|
|
1427
1313
|
|
|
1428
|
-
if response_cache
|
|
1314
|
+
if response_cache
|
|
1429
1315
|
response, created_at = response_cache
|
|
1430
1316
|
|
|
1431
|
-
if Time.new - created_at < @expire_resolv_cache
|
|
1432
|
-
response[
|
|
1433
|
-
send_data(
|
|
1317
|
+
if Time.new - created_at < @expire_resolv_cache
|
|
1318
|
+
response[0, 2] = id
|
|
1319
|
+
send_data(@rsvd, response, addrinfo)
|
|
1434
1320
|
return
|
|
1435
1321
|
end
|
|
1436
1322
|
|
|
1437
|
-
if type == 1
|
|
1438
|
-
@response_caches.delete(
|
|
1323
|
+
if type == 1
|
|
1324
|
+
@response_caches.delete(domain)
|
|
1439
1325
|
else
|
|
1440
|
-
@response6_caches.delete(
|
|
1326
|
+
@response6_caches.delete(domain)
|
|
1441
1327
|
end
|
|
1442
1328
|
end
|
|
1443
1329
|
|
|
1444
|
-
if @remotes.any?{
|
|
1330
|
+
if @remotes.any?{|r| domain.include?(r)}
|
|
1445
1331
|
check_expire_nears
|
|
1446
|
-
near_id = rand(
|
|
1447
|
-
|
|
1448
|
-
near_info = {
|
|
1332
|
+
near_id = rand((2 ** 64) - 2) + 1
|
|
1333
|
+
@near_infos[near_id] = {
|
|
1449
1334
|
addrinfo: addrinfo,
|
|
1450
1335
|
created_at: Time.new,
|
|
1451
1336
|
domain: domain,
|
|
1452
1337
|
id: id,
|
|
1453
1338
|
type: type
|
|
1454
1339
|
}
|
|
1455
|
-
|
|
1456
|
-
@
|
|
1457
|
-
|
|
1458
|
-
msg = "#{ @h_query }#{ [ near_id, type ].pack( 'Q>C' ) }#{ domain }"
|
|
1459
|
-
add_proxy_wbuff( pack_a_chunk( msg ) )
|
|
1340
|
+
puts "add h_query #{near_id} #{type} #{domain}" if @is_debug
|
|
1341
|
+
msg = "#{@h_query}#{[near_id, type].pack('Q>C')}#{domain}"
|
|
1342
|
+
add_proxy_wbuff(pack_a_chunk(msg))
|
|
1460
1343
|
return
|
|
1461
1344
|
end
|
|
1462
1345
|
|
|
1463
|
-
new_a_rsv(
|
|
1346
|
+
new_a_rsv(data, addrinfo, domain, type)
|
|
1464
1347
|
end
|
|
1465
1348
|
|
|
1466
|
-
def read_src(
|
|
1349
|
+
def read_src(src)
|
|
1467
1350
|
begin
|
|
1468
|
-
data = src.read_nonblock(
|
|
1351
|
+
data = src.read_nonblock(READ_SIZE)
|
|
1469
1352
|
rescue Errno::ENOTCONN => e
|
|
1470
1353
|
return
|
|
1471
1354
|
rescue Exception => e
|
|
1472
|
-
|
|
1355
|
+
puts "read src #{e.class}" if @is_debug
|
|
1356
|
+
close_src(src)
|
|
1473
1357
|
return
|
|
1474
1358
|
end
|
|
1475
1359
|
|
|
1476
|
-
set_update(
|
|
1477
|
-
src_info = @src_infos[
|
|
1478
|
-
proxy_type = src_info[
|
|
1360
|
+
set_update(src)
|
|
1361
|
+
src_info = @src_infos[src]
|
|
1362
|
+
proxy_type = src_info[:proxy_type]
|
|
1479
1363
|
|
|
1480
1364
|
case proxy_type
|
|
1481
|
-
when :uncheck
|
|
1482
|
-
if data[
|
|
1483
|
-
domain_port = data.split(
|
|
1365
|
+
when :uncheck
|
|
1366
|
+
if data[0, 7] == 'CONNECT'
|
|
1367
|
+
domain_port = data.split("\r\n")[0].split(' ')[1]
|
|
1484
1368
|
|
|
1485
|
-
unless domain_port
|
|
1369
|
+
unless domain_port
|
|
1486
1370
|
puts "CONNECT miss domain"
|
|
1487
|
-
close_src(
|
|
1371
|
+
close_src(src)
|
|
1488
1372
|
return
|
|
1489
1373
|
end
|
|
1490
|
-
elsif data[
|
|
1374
|
+
elsif data[0].unpack('C').first == 5
|
|
1491
1375
|
# https://tools.ietf.org/html/rfc1928
|
|
1492
1376
|
#
|
|
1493
1377
|
# +----+----------+----------+
|
|
@@ -1495,12 +1379,12 @@ module Girl
|
|
|
1495
1379
|
# +----+----------+----------+
|
|
1496
1380
|
# | 1 | 1 | 1 to 255 |
|
|
1497
1381
|
# +----+----------+----------+
|
|
1498
|
-
nmethods = data[
|
|
1499
|
-
methods = data[
|
|
1382
|
+
nmethods = data[1].unpack('C').first
|
|
1383
|
+
methods = data[2, nmethods].unpack('C*')
|
|
1500
1384
|
|
|
1501
|
-
unless methods.include?(
|
|
1385
|
+
unless methods.include?(0)
|
|
1502
1386
|
puts "miss method 00"
|
|
1503
|
-
close_src(
|
|
1387
|
+
close_src(src)
|
|
1504
1388
|
return
|
|
1505
1389
|
end
|
|
1506
1390
|
|
|
@@ -1509,161 +1393,163 @@ module Girl
|
|
|
1509
1393
|
# +----+--------+
|
|
1510
1394
|
# | 1 | 1 |
|
|
1511
1395
|
# +----+--------+
|
|
1512
|
-
puts "read src version 5 nmethods #{
|
|
1513
|
-
data2 = [
|
|
1514
|
-
add_src_wbuff(
|
|
1396
|
+
puts "read src version 5 nmethods #{nmethods} methods #{methods.inspect}" if @is_debug
|
|
1397
|
+
data2 = [5, 0].pack('CC')
|
|
1398
|
+
add_src_wbuff(src, data2)
|
|
1515
1399
|
return if src.closed?
|
|
1516
|
-
src_info[
|
|
1517
|
-
src_info[
|
|
1400
|
+
src_info[:proxy_proto] = :socks5
|
|
1401
|
+
src_info[:proxy_type] = :negotiation
|
|
1518
1402
|
return
|
|
1519
1403
|
else
|
|
1520
|
-
host_line = data.split(
|
|
1404
|
+
host_line = data.split("\r\n").find{|_line| _line[0, 6] == 'Host: '}
|
|
1521
1405
|
|
|
1522
|
-
unless host_line
|
|
1523
|
-
close_src(
|
|
1406
|
+
unless host_line
|
|
1407
|
+
close_src(src)
|
|
1524
1408
|
return
|
|
1525
1409
|
end
|
|
1526
1410
|
|
|
1527
|
-
lines = data.split(
|
|
1411
|
+
lines = data.split("\r\n")
|
|
1528
1412
|
|
|
1529
|
-
unless lines.empty?
|
|
1530
|
-
method, url, proto = lines.first.split(
|
|
1413
|
+
unless lines.empty?
|
|
1414
|
+
method, url, proto = lines.first.split(' ')
|
|
1531
1415
|
|
|
1532
|
-
if proto && url && proto[
|
|
1533
|
-
domain_port = url.split(
|
|
1416
|
+
if proto && url && proto[0, 4] == 'HTTP' && url[0, 7] == 'http://'
|
|
1417
|
+
domain_port = url.split('/')[2]
|
|
1534
1418
|
end
|
|
1535
1419
|
end
|
|
1536
1420
|
|
|
1537
|
-
unless domain_port
|
|
1538
|
-
domain_port = host_line.split(
|
|
1421
|
+
unless domain_port
|
|
1422
|
+
domain_port = host_line.split(' ')[1]
|
|
1539
1423
|
|
|
1540
|
-
unless domain_port
|
|
1424
|
+
unless domain_port
|
|
1541
1425
|
puts "Host line miss domain"
|
|
1542
|
-
close_src(
|
|
1426
|
+
close_src(src)
|
|
1543
1427
|
return
|
|
1544
1428
|
end
|
|
1545
1429
|
end
|
|
1546
1430
|
|
|
1547
|
-
src_info[
|
|
1548
|
-
add_src_rbuff(
|
|
1431
|
+
src_info[:is_connect] = false
|
|
1432
|
+
add_src_rbuff(src, data)
|
|
1549
1433
|
end
|
|
1550
1434
|
|
|
1551
|
-
colon_idx = domain_port.rindex(
|
|
1552
|
-
close_idx = domain_port.rindex(
|
|
1435
|
+
colon_idx = domain_port.rindex(':')
|
|
1436
|
+
close_idx = domain_port.rindex(']')
|
|
1553
1437
|
|
|
1554
|
-
if colon_idx && (
|
|
1555
|
-
domain = domain_port[
|
|
1556
|
-
port = domain_port[
|
|
1438
|
+
if colon_idx && (close_idx.nil? || (colon_idx > close_idx))
|
|
1439
|
+
domain = domain_port[0...colon_idx]
|
|
1440
|
+
port = domain_port[(colon_idx + 1)..-1].to_i
|
|
1557
1441
|
else
|
|
1558
1442
|
domain = domain_port
|
|
1559
1443
|
port = 80
|
|
1560
1444
|
end
|
|
1561
1445
|
|
|
1562
|
-
domain = domain.gsub(
|
|
1563
|
-
src_info[
|
|
1564
|
-
src_info[
|
|
1565
|
-
src_info[
|
|
1566
|
-
resolve_domain(
|
|
1567
|
-
when :checking
|
|
1568
|
-
add_src_rbuff(
|
|
1569
|
-
when :negotiation
|
|
1446
|
+
domain = domain.gsub(/\[|\]/, '')
|
|
1447
|
+
src_info[:proxy_proto] = :http
|
|
1448
|
+
src_info[:destination_domain] = domain
|
|
1449
|
+
src_info[:destination_port] = port
|
|
1450
|
+
resolve_domain(domain, src)
|
|
1451
|
+
when :checking
|
|
1452
|
+
add_src_rbuff(src, data)
|
|
1453
|
+
when :negotiation
|
|
1570
1454
|
# +----+-----+-------+------+----------+----------+
|
|
1571
1455
|
# |VER | CMD | RSV | ATYP | DST.ADDR | DST.PORT |
|
|
1572
1456
|
# +----+-----+-------+------+----------+----------+
|
|
1573
1457
|
# | 1 | 1 | X'00' | 1 | Variable | 2 |
|
|
1574
1458
|
# +----+-----+-------+------+----------+----------+
|
|
1575
|
-
ver, cmd, rsv, atyp = data[
|
|
1459
|
+
ver, cmd, rsv, atyp = data[0, 4].unpack('C4')
|
|
1576
1460
|
|
|
1577
|
-
if cmd == 1
|
|
1578
|
-
if atyp == 1
|
|
1579
|
-
destination_host, destination_port = data[
|
|
1461
|
+
if cmd == 1
|
|
1462
|
+
if atyp == 1
|
|
1463
|
+
destination_host, destination_port = data[4, 6].unpack('Nn')
|
|
1580
1464
|
|
|
1581
1465
|
begin
|
|
1582
|
-
destination_addr = Socket.sockaddr_in(
|
|
1583
|
-
destination_addrinfo = Addrinfo.new(
|
|
1466
|
+
destination_addr = Socket.sockaddr_in(destination_port, destination_host)
|
|
1467
|
+
destination_addrinfo = Addrinfo.new(destination_addr)
|
|
1584
1468
|
rescue Exception => e
|
|
1585
|
-
puts "new addrinfo #{
|
|
1586
|
-
close_src(
|
|
1469
|
+
puts "new addrinfo #{e.class}"
|
|
1470
|
+
close_src(src)
|
|
1587
1471
|
return
|
|
1588
1472
|
end
|
|
1589
1473
|
|
|
1590
1474
|
destination_ip = destination_addrinfo.ip_address
|
|
1591
|
-
puts "read src cmd #{
|
|
1592
|
-
src_info[
|
|
1593
|
-
src_info[
|
|
1594
|
-
make_tunnel(
|
|
1595
|
-
elsif atyp == 3
|
|
1596
|
-
domain_len = data[
|
|
1597
|
-
|
|
1598
|
-
if (
|
|
1599
|
-
domain = data[
|
|
1600
|
-
port = data[
|
|
1601
|
-
puts "read src cmd #{
|
|
1602
|
-
src_info[
|
|
1603
|
-
src_info[
|
|
1604
|
-
resolve_domain(
|
|
1475
|
+
puts "read src cmd #{cmd} atyp #{atyp} #{destination_ip} #{destination_port}" if @is_debug
|
|
1476
|
+
src_info[:destination_domain] = destination_ip
|
|
1477
|
+
src_info[:destination_port] = destination_port
|
|
1478
|
+
make_tunnel(destination_ip, src)
|
|
1479
|
+
elsif atyp == 3
|
|
1480
|
+
domain_len = data[4].unpack('C').first
|
|
1481
|
+
|
|
1482
|
+
if (domain_len + 7) == data.bytesize
|
|
1483
|
+
domain = data[5, domain_len]
|
|
1484
|
+
port = data[(5 + domain_len), 2].unpack('n').first
|
|
1485
|
+
puts "read src cmd #{cmd} atyp #{atyp} #{domain} #{port}" if @is_debug
|
|
1486
|
+
src_info[:destination_domain] = domain
|
|
1487
|
+
src_info[:destination_port] = port
|
|
1488
|
+
resolve_domain(domain, src)
|
|
1605
1489
|
end
|
|
1606
1490
|
else
|
|
1607
|
-
puts "socks5 atyp #{
|
|
1608
|
-
close_src(
|
|
1491
|
+
puts "socks5 atyp #{atyp} not implement"
|
|
1492
|
+
close_src(src)
|
|
1609
1493
|
end
|
|
1610
1494
|
else
|
|
1611
|
-
puts "socks5 cmd #{
|
|
1612
|
-
close_src(
|
|
1495
|
+
puts "socks5 cmd #{cmd} not implement"
|
|
1496
|
+
close_src(src)
|
|
1613
1497
|
end
|
|
1614
|
-
when :remote
|
|
1615
|
-
|
|
1616
|
-
|
|
1617
|
-
|
|
1618
|
-
|
|
1619
|
-
|
|
1620
|
-
|
|
1621
|
-
|
|
1622
|
-
|
|
1623
|
-
|
|
1624
|
-
|
|
1625
|
-
|
|
1626
|
-
|
|
1498
|
+
when :remote
|
|
1499
|
+
src_info[:in] += data.bytesize
|
|
1500
|
+
domain = src_info[:destination_domain]
|
|
1501
|
+
|
|
1502
|
+
if !src_info[:is_big] && (src_info[:in] >= READ_SIZE)
|
|
1503
|
+
puts "set src is big #{domain}"
|
|
1504
|
+
src_info[:is_big] = true
|
|
1505
|
+
end
|
|
1506
|
+
|
|
1507
|
+
src_id = src_info[:src_id]
|
|
1508
|
+
data = pack_traffic(src_id, data)
|
|
1509
|
+
|
|
1510
|
+
if src_info[:is_big]
|
|
1511
|
+
add_big_wbuff(data)
|
|
1512
|
+
else
|
|
1513
|
+
add_proxy_wbuff(data)
|
|
1627
1514
|
end
|
|
1628
|
-
when :direct
|
|
1629
|
-
dst = src_info[
|
|
1515
|
+
when :direct
|
|
1516
|
+
dst = src_info[:dst]
|
|
1630
1517
|
|
|
1631
|
-
if dst
|
|
1632
|
-
add_dst_wbuff(
|
|
1518
|
+
if dst
|
|
1519
|
+
add_dst_wbuff(dst, data)
|
|
1633
1520
|
else
|
|
1634
|
-
add_src_rbuff(
|
|
1521
|
+
add_src_rbuff(src, data)
|
|
1635
1522
|
end
|
|
1636
1523
|
end
|
|
1637
1524
|
end
|
|
1638
1525
|
|
|
1639
|
-
def read_tspd(
|
|
1526
|
+
def read_tspd(tspd)
|
|
1640
1527
|
check_expire_srcs
|
|
1641
1528
|
|
|
1642
1529
|
begin
|
|
1643
1530
|
src, addrinfo = tspd.accept_nonblock
|
|
1644
1531
|
rescue IO::WaitReadable, Errno::EINTR => e
|
|
1645
|
-
puts "tspd accept #{
|
|
1532
|
+
puts "tspd accept #{e.class}"
|
|
1646
1533
|
return
|
|
1647
1534
|
end
|
|
1648
1535
|
|
|
1649
|
-
puts "tspd accept a src #{
|
|
1536
|
+
puts "tspd accept a src #{addrinfo.ip_unpack.inspect}" if @is_debug
|
|
1650
1537
|
|
|
1651
1538
|
begin
|
|
1652
1539
|
# /usr/include/linux/netfilter_ipv4.h
|
|
1653
|
-
option = src.getsockopt(
|
|
1540
|
+
option = src.getsockopt(Socket::SOL_IP, 80)
|
|
1654
1541
|
rescue Exception => e
|
|
1655
|
-
puts "get SO_ORIGINAL_DST #{
|
|
1542
|
+
puts "get SO_ORIGINAL_DST #{e.class} #{addrinfo.ip_unpack.inspect}"
|
|
1656
1543
|
src.close
|
|
1657
1544
|
return
|
|
1658
1545
|
end
|
|
1659
1546
|
|
|
1660
|
-
dest_family, dest_port, dest_host = option.unpack(
|
|
1661
|
-
dest_addr = Socket.sockaddr_in(
|
|
1662
|
-
dest_addrinfo = Addrinfo.new(
|
|
1547
|
+
dest_family, dest_port, dest_host = option.unpack('nnN')
|
|
1548
|
+
dest_addr = Socket.sockaddr_in(dest_port, dest_host)
|
|
1549
|
+
dest_addrinfo = Addrinfo.new(dest_addr)
|
|
1663
1550
|
dest_ip = dest_addrinfo.ip_address
|
|
1664
|
-
src_id = rand(
|
|
1665
|
-
|
|
1666
|
-
src_info = {
|
|
1551
|
+
src_id = rand((2 ** 64) - 2) + 1
|
|
1552
|
+
@src_infos[src] = {
|
|
1667
1553
|
addrinfo: addrinfo,
|
|
1668
1554
|
closing: false,
|
|
1669
1555
|
destination_domain: dest_ip,
|
|
@@ -1677,195 +1563,166 @@ module Girl
|
|
|
1677
1563
|
src_id: src_id,
|
|
1678
1564
|
wbuff: ''
|
|
1679
1565
|
}
|
|
1680
|
-
|
|
1681
|
-
|
|
1682
|
-
add_read( src, :src )
|
|
1683
|
-
make_tunnel( dest_ip, src )
|
|
1566
|
+
add_read(src, :src)
|
|
1567
|
+
make_tunnel(dest_ip, src)
|
|
1684
1568
|
end
|
|
1685
1569
|
|
|
1686
|
-
def resolve_domain(
|
|
1570
|
+
def resolve_domain(domain, src)
|
|
1687
1571
|
return if src.nil? || src.closed?
|
|
1688
1572
|
|
|
1689
|
-
unless domain =~ /^(?=^.{3,255}$)[a-zA-Z0-9][-a-zA-Z0-9]{0,62}(\.[a-zA-Z0-9][-a-zA-Z0-9]{0,62})+$/
|
|
1573
|
+
unless domain =~ /^(?=^.{3,255}$)[a-zA-Z0-9][-a-zA-Z0-9]{0,62}(\.[a-zA-Z0-9][-a-zA-Z0-9]{0,62})+$/
|
|
1690
1574
|
# 忽略非法域名
|
|
1691
|
-
puts "ignore #{
|
|
1692
|
-
close_src(
|
|
1575
|
+
puts "ignore #{domain}"
|
|
1576
|
+
close_src(src)
|
|
1693
1577
|
return
|
|
1694
1578
|
end
|
|
1695
1579
|
|
|
1696
|
-
if domain == 'localhost'
|
|
1697
|
-
domain = "127.0.0.1"
|
|
1698
|
-
end
|
|
1580
|
+
domain =' 127.0.0.1' if domain == 'localhost'
|
|
1699
1581
|
|
|
1700
|
-
if domain =~ /^\d{1,3}\.\d{1,3}\.\d{1,3}.\d{1,3}$/
|
|
1582
|
+
if domain =~ /^\d{1,3}\.\d{1,3}\.\d{1,3}.\d{1,3}$/
|
|
1701
1583
|
# ipv4
|
|
1702
|
-
make_tunnel(
|
|
1584
|
+
make_tunnel(domain, src)
|
|
1703
1585
|
return
|
|
1704
1586
|
end
|
|
1705
1587
|
|
|
1706
|
-
if @remotes.any?{
|
|
1707
|
-
set_remote(
|
|
1588
|
+
if @remotes.any?{|remote| (domain.size >= remote.size) && (domain[(remote.size * -1)..-1] == remote)}
|
|
1589
|
+
set_remote(src)
|
|
1708
1590
|
return
|
|
1709
1591
|
end
|
|
1710
1592
|
|
|
1711
|
-
resolv_cache = @resolv_caches[
|
|
1593
|
+
resolv_cache = @resolv_caches[domain]
|
|
1712
1594
|
|
|
1713
|
-
if resolv_cache
|
|
1595
|
+
if resolv_cache
|
|
1714
1596
|
ip, created_at = resolv_cache
|
|
1715
1597
|
|
|
1716
|
-
if Time.new - created_at < @expire_resolv_cache
|
|
1717
|
-
make_tunnel(
|
|
1598
|
+
if Time.new - created_at < @expire_resolv_cache
|
|
1599
|
+
make_tunnel(ip, src)
|
|
1718
1600
|
return
|
|
1719
1601
|
end
|
|
1720
1602
|
|
|
1721
|
-
@resolv_caches.delete(
|
|
1603
|
+
@resolv_caches.delete(domain)
|
|
1722
1604
|
end
|
|
1723
1605
|
|
|
1724
1606
|
begin
|
|
1725
|
-
data = pack_a_query(
|
|
1607
|
+
data = pack_a_query(domain)
|
|
1726
1608
|
rescue Exception => e
|
|
1727
|
-
puts "pack a query #{
|
|
1728
|
-
close_src(
|
|
1609
|
+
puts "pack a query #{e.class} #{e.message} #{domain}"
|
|
1610
|
+
close_src(src)
|
|
1729
1611
|
return
|
|
1730
1612
|
end
|
|
1731
1613
|
|
|
1732
1614
|
check_expire_dnses
|
|
1733
|
-
dns = Socket.new(
|
|
1615
|
+
dns = Socket.new(Socket::AF_INET, Socket::SOCK_DGRAM, 0)
|
|
1734
1616
|
|
|
1735
1617
|
begin
|
|
1736
|
-
@nameserver_addrs.each{
|
|
1618
|
+
@nameserver_addrs.each{|addr| dns.sendmsg(data, 0, addr)}
|
|
1737
1619
|
rescue Exception => e
|
|
1738
|
-
puts "dns send data #{
|
|
1620
|
+
puts "dns send data #{e.class}"
|
|
1739
1621
|
dns.close
|
|
1740
|
-
close_src(
|
|
1622
|
+
close_src(src)
|
|
1741
1623
|
return
|
|
1742
1624
|
end
|
|
1743
1625
|
|
|
1744
|
-
|
|
1626
|
+
@dns_infos[dns] = {
|
|
1745
1627
|
domain: domain,
|
|
1746
1628
|
src: src
|
|
1747
1629
|
}
|
|
1748
|
-
|
|
1749
|
-
@
|
|
1750
|
-
|
|
1751
|
-
src_info = @src_infos[ src ]
|
|
1752
|
-
src_info[ :proxy_type ] = :checking
|
|
1630
|
+
add_read(dns, :dns)
|
|
1631
|
+
src_info = @src_infos[src]
|
|
1632
|
+
src_info[:proxy_type] = :checking
|
|
1753
1633
|
end
|
|
1754
1634
|
|
|
1755
|
-
def send_data(
|
|
1635
|
+
def send_data(sock, data, target_addr)
|
|
1756
1636
|
begin
|
|
1757
|
-
sock.sendmsg(
|
|
1637
|
+
sock.sendmsg(data, 0, target_addr)
|
|
1758
1638
|
rescue Exception => e
|
|
1759
|
-
puts "sendmsg #{
|
|
1639
|
+
puts "sendmsg #{e.class}"
|
|
1760
1640
|
end
|
|
1761
1641
|
end
|
|
1762
1642
|
|
|
1763
|
-
def set_dst_closing(
|
|
1643
|
+
def set_dst_closing(dst)
|
|
1764
1644
|
return if dst.nil? || dst.closed?
|
|
1765
|
-
dst_info = @dst_infos[
|
|
1766
|
-
return if dst_info.nil? || dst_info[
|
|
1767
|
-
dst_info[
|
|
1768
|
-
add_write(
|
|
1769
|
-
end
|
|
1770
|
-
|
|
1771
|
-
def set_girl_closing( girl )
|
|
1772
|
-
return if girl.nil? || girl.closed?
|
|
1773
|
-
girl_info = @girl_infos[ girl ]
|
|
1774
|
-
return if girl_info.nil? || girl_info[ :closing ]
|
|
1775
|
-
girl_info[ :closing ] = true
|
|
1776
|
-
add_write( girl )
|
|
1645
|
+
dst_info = @dst_infos[dst]
|
|
1646
|
+
return if dst_info.nil? || dst_info[:closing]
|
|
1647
|
+
dst_info[:closing] = true
|
|
1648
|
+
add_write(dst)
|
|
1777
1649
|
end
|
|
1778
1650
|
|
|
1779
|
-
def set_p1_closing(
|
|
1651
|
+
def set_p1_closing(p1)
|
|
1780
1652
|
return if p1.nil? || p1.closed?
|
|
1781
|
-
p1_info = @p1_infos[
|
|
1782
|
-
return if p1_info.nil? || p1_info[
|
|
1783
|
-
p1_info[
|
|
1784
|
-
add_write(
|
|
1653
|
+
p1_info = @p1_infos[p1]
|
|
1654
|
+
return if p1_info.nil? || p1_info[:closing]
|
|
1655
|
+
p1_info[:closing] = true
|
|
1656
|
+
add_write(p1)
|
|
1785
1657
|
end
|
|
1786
1658
|
|
|
1787
|
-
def
|
|
1788
|
-
return if relay.nil? || relay.closed?
|
|
1789
|
-
relay_info = @relay_infos[ relay ]
|
|
1790
|
-
return if relay_info.nil? || relay_info[ :closing ]
|
|
1791
|
-
relay_info[ :closing ] = true
|
|
1792
|
-
add_write( relay )
|
|
1793
|
-
end
|
|
1794
|
-
|
|
1795
|
-
def set_remote( src )
|
|
1659
|
+
def set_remote(src)
|
|
1796
1660
|
return if src.nil? || src.closed?
|
|
1797
1661
|
|
|
1798
|
-
if @proxy.closed?
|
|
1799
|
-
close_src(
|
|
1662
|
+
if @proxy.closed?
|
|
1663
|
+
close_src(src)
|
|
1800
1664
|
return
|
|
1801
1665
|
end
|
|
1802
1666
|
|
|
1803
|
-
src_info = @src_infos[
|
|
1804
|
-
src_info[
|
|
1667
|
+
src_info = @src_infos[src]
|
|
1668
|
+
src_info[:proxy_type] = :remote
|
|
1805
1669
|
|
|
1806
|
-
if src_info[
|
|
1807
|
-
if src_info[
|
|
1808
|
-
puts "add HTTP_OK #{
|
|
1809
|
-
add_src_wbuff(
|
|
1670
|
+
if src_info[:proxy_proto] == :http
|
|
1671
|
+
if src_info[:is_connect]
|
|
1672
|
+
puts "add HTTP_OK #{src_info[:proxy_type]}" if @is_debug
|
|
1673
|
+
add_src_wbuff(src, HTTP_OK)
|
|
1810
1674
|
end
|
|
1811
|
-
elsif src_info[
|
|
1812
|
-
puts "add_socks5_conn_reply #{
|
|
1813
|
-
add_socks5_conn_reply(
|
|
1675
|
+
elsif src_info[:proxy_proto] == :socks5
|
|
1676
|
+
puts "add_socks5_conn_reply #{src_info[:proxy_type]}" if @is_debug
|
|
1677
|
+
add_socks5_conn_reply(src)
|
|
1814
1678
|
end
|
|
1815
1679
|
|
|
1816
|
-
src_id = src_info[
|
|
1817
|
-
domain = src_info[
|
|
1818
|
-
port = src_info[
|
|
1819
|
-
domain_port = [
|
|
1820
|
-
puts "add h_a_new_source #{
|
|
1821
|
-
msg = "#{
|
|
1822
|
-
add_proxy_wbuff(
|
|
1823
|
-
data = src_info[
|
|
1680
|
+
src_id = src_info[:src_id]
|
|
1681
|
+
domain = src_info[:destination_domain]
|
|
1682
|
+
port = src_info[:destination_port]
|
|
1683
|
+
domain_port = [domain, port].join(':')
|
|
1684
|
+
puts "add h_a_new_source #{src_id} #{domain_port}" if @is_debug
|
|
1685
|
+
msg = "#{@h_a_new_source}#{[src_id].pack('Q>')}#{domain_port}"
|
|
1686
|
+
add_proxy_wbuff(pack_a_chunk(msg))
|
|
1687
|
+
data = src_info[:rbuff].dup
|
|
1824
1688
|
|
|
1825
|
-
unless data.empty?
|
|
1826
|
-
puts "move src rbuff to proxy #{
|
|
1827
|
-
add_proxy_wbuff(
|
|
1689
|
+
unless data.empty?
|
|
1690
|
+
puts "move src rbuff to proxy #{domain} #{data.bytesize}" if @is_debug
|
|
1691
|
+
add_proxy_wbuff(pack_traffic(src_id, data))
|
|
1828
1692
|
end
|
|
1829
1693
|
end
|
|
1830
1694
|
|
|
1831
|
-
def set_src_closing(
|
|
1695
|
+
def set_src_closing(src)
|
|
1832
1696
|
return if src.nil? || src.closed?
|
|
1833
|
-
src_info = @src_infos[
|
|
1834
|
-
return if src_info.nil? || src_info[
|
|
1835
|
-
src_info[
|
|
1836
|
-
add_write(
|
|
1697
|
+
src_info = @src_infos[src]
|
|
1698
|
+
return if src_info.nil? || src_info[:closing]
|
|
1699
|
+
src_info[:closing] = true
|
|
1700
|
+
add_write(src)
|
|
1837
1701
|
end
|
|
1838
1702
|
|
|
1839
|
-
def set_update(
|
|
1840
|
-
@updates[
|
|
1841
|
-
|
|
1842
|
-
if @updates_limit - @updates.size <= 20 then
|
|
1843
|
-
puts "updates #{ @updates.size }"
|
|
1844
|
-
end
|
|
1703
|
+
def set_update(sock)
|
|
1704
|
+
@updates[sock] = Time.new
|
|
1705
|
+
puts "updates #{@updates.size}" if @updates_limit - @updates.size <= 20
|
|
1845
1706
|
|
|
1846
|
-
if @updates.size >= @updates_limit
|
|
1707
|
+
if @updates.size >= @updates_limit
|
|
1847
1708
|
puts "eliminate updates"
|
|
1848
1709
|
|
|
1849
|
-
@updates.keys.each do |
|
|
1850
|
-
case @roles[
|
|
1710
|
+
@updates.keys.each do |_sock|
|
|
1711
|
+
case @roles[_sock]
|
|
1851
1712
|
when :dns
|
|
1852
|
-
close_dns(
|
|
1713
|
+
close_dns(_sock)
|
|
1853
1714
|
when :dst
|
|
1854
|
-
close_dst(
|
|
1855
|
-
when :girl
|
|
1856
|
-
close_girl( _sock )
|
|
1715
|
+
close_dst(_sock)
|
|
1857
1716
|
when :mem
|
|
1858
|
-
close_mem(
|
|
1717
|
+
close_mem(_sock)
|
|
1859
1718
|
when :p1
|
|
1860
|
-
close_p1(
|
|
1861
|
-
when :relay
|
|
1862
|
-
close_relay( _sock )
|
|
1719
|
+
close_p1(_sock)
|
|
1863
1720
|
when :rsv
|
|
1864
|
-
close_rsv(
|
|
1721
|
+
close_rsv(_sock)
|
|
1865
1722
|
when :src
|
|
1866
|
-
close_src(
|
|
1723
|
+
close_src(_sock)
|
|
1867
1724
|
else
|
|
1868
|
-
close_sock(
|
|
1725
|
+
close_sock(_sock)
|
|
1869
1726
|
end
|
|
1870
1727
|
end
|
|
1871
1728
|
|
|
@@ -1873,301 +1730,263 @@ module Girl
|
|
|
1873
1730
|
end
|
|
1874
1731
|
end
|
|
1875
1732
|
|
|
1876
|
-
|
|
1877
|
-
|
|
1878
|
-
|
|
1733
|
+
def write_big(big)
|
|
1734
|
+
big_info = @big_infos[big]
|
|
1735
|
+
|
|
1736
|
+
unless big_info
|
|
1737
|
+
puts "big info not found delete big"
|
|
1738
|
+
@writes.delete(big)
|
|
1879
1739
|
return
|
|
1880
1740
|
end
|
|
1881
1741
|
|
|
1882
|
-
|
|
1883
|
-
|
|
1884
|
-
data =
|
|
1885
|
-
|
|
1886
|
-
if data.empty? then
|
|
1887
|
-
if dst_info[ :closing ] then
|
|
1888
|
-
close_dst( dst )
|
|
1889
|
-
else
|
|
1890
|
-
@writes.delete( dst )
|
|
1891
|
-
end
|
|
1742
|
+
return if @writes.include?(@proxy)
|
|
1743
|
+
|
|
1744
|
+
data = big_info[:wbuff]
|
|
1892
1745
|
|
|
1746
|
+
if data.empty?
|
|
1747
|
+
@writes.delete(big)
|
|
1893
1748
|
return
|
|
1894
1749
|
end
|
|
1895
1750
|
|
|
1896
1751
|
begin
|
|
1897
|
-
|
|
1752
|
+
if big_info[:is_syn]
|
|
1753
|
+
written = big.sendmsg_nonblock(data, 536870912, @bigd_addr)
|
|
1754
|
+
big_info[:is_syn] = false
|
|
1755
|
+
else
|
|
1756
|
+
written = big.write_nonblock(data)
|
|
1757
|
+
end
|
|
1898
1758
|
rescue Errno::EINPROGRESS
|
|
1899
1759
|
return
|
|
1900
1760
|
rescue Exception => e
|
|
1901
|
-
|
|
1761
|
+
puts "write big #{e.class}" if @is_debug
|
|
1762
|
+
close_big(big)
|
|
1902
1763
|
return
|
|
1903
1764
|
end
|
|
1904
1765
|
|
|
1905
|
-
set_update(
|
|
1906
|
-
data = data[
|
|
1907
|
-
|
|
1908
|
-
bytesize = dst_info[ :wbuff ].bytesize
|
|
1766
|
+
set_update(big)
|
|
1767
|
+
data = data[written..-1]
|
|
1768
|
+
big_info[:wbuff] = data
|
|
1909
1769
|
|
|
1910
|
-
if
|
|
1911
|
-
puts "
|
|
1912
|
-
|
|
1913
|
-
|
|
1770
|
+
if big_info[:wbuff].empty? && big_info[:overflowing]
|
|
1771
|
+
puts "big empty"
|
|
1772
|
+
big_info[:overflowing] = false
|
|
1773
|
+
|
|
1774
|
+
@src_infos.select{|_, info| info[:is_big]}.each do |src, info|
|
|
1775
|
+
puts "resume src #{info[:destination_domain]}"
|
|
1776
|
+
add_read(src)
|
|
1777
|
+
end
|
|
1778
|
+
|
|
1779
|
+
@p1_infos.select{|_, info| info[:is_big]}.each do |p1, info|
|
|
1780
|
+
puts "resume p1 #{info[:p2_id]}"
|
|
1781
|
+
add_read(p1)
|
|
1782
|
+
end
|
|
1914
1783
|
end
|
|
1915
1784
|
end
|
|
1916
1785
|
|
|
1917
|
-
def
|
|
1918
|
-
|
|
1919
|
-
|
|
1786
|
+
def write_dst(dst)
|
|
1787
|
+
dst_info = @dst_infos[dst]
|
|
1788
|
+
|
|
1789
|
+
unless dst_info
|
|
1790
|
+
puts "dst info not found delete dst"
|
|
1791
|
+
@writes.delete(dst)
|
|
1920
1792
|
return
|
|
1921
1793
|
end
|
|
1922
1794
|
|
|
1923
|
-
|
|
1924
|
-
|
|
1925
|
-
data = girl_info[ :wbuff ]
|
|
1795
|
+
dst_info[:connected] = true
|
|
1796
|
+
data = dst_info[:wbuff]
|
|
1926
1797
|
|
|
1927
|
-
if data.empty?
|
|
1928
|
-
if
|
|
1929
|
-
|
|
1798
|
+
if data.empty?
|
|
1799
|
+
if dst_info[:closing]
|
|
1800
|
+
close_dst(dst)
|
|
1930
1801
|
else
|
|
1931
|
-
@writes.delete(
|
|
1802
|
+
@writes.delete(dst)
|
|
1932
1803
|
end
|
|
1933
1804
|
|
|
1934
1805
|
return
|
|
1935
1806
|
end
|
|
1936
1807
|
|
|
1937
1808
|
begin
|
|
1938
|
-
|
|
1939
|
-
written = girl.sendmsg_nonblock( data, 536870912, @proxyd_addr )
|
|
1940
|
-
girl_info[ :is_syn ] = false
|
|
1941
|
-
else
|
|
1942
|
-
written = girl.write_nonblock( data )
|
|
1943
|
-
end
|
|
1809
|
+
written = dst.write_nonblock(data)
|
|
1944
1810
|
rescue Errno::EINPROGRESS
|
|
1945
1811
|
return
|
|
1946
1812
|
rescue Exception => e
|
|
1947
|
-
|
|
1813
|
+
puts "write dst #{e.class}" if @is_debug
|
|
1814
|
+
close_dst(dst)
|
|
1948
1815
|
return
|
|
1949
1816
|
end
|
|
1950
1817
|
|
|
1951
|
-
set_update(
|
|
1952
|
-
data = data[
|
|
1953
|
-
|
|
1954
|
-
|
|
1818
|
+
set_update(dst)
|
|
1819
|
+
data = data[written..-1]
|
|
1820
|
+
dst_info[:wbuff] = data
|
|
1821
|
+
domain = dst_info[:domain]
|
|
1955
1822
|
|
|
1956
|
-
if
|
|
1957
|
-
puts "
|
|
1958
|
-
|
|
1959
|
-
|
|
1823
|
+
if dst_info[:overflowing] && dst_info[:wbuff].empty?
|
|
1824
|
+
puts "dst empty #{domain}"
|
|
1825
|
+
dst_info[:overflowing] = false
|
|
1826
|
+
puts "resume src"
|
|
1827
|
+
add_read(dst_info[:src])
|
|
1960
1828
|
end
|
|
1961
1829
|
end
|
|
1962
1830
|
|
|
1963
|
-
def write_mem(
|
|
1964
|
-
|
|
1965
|
-
|
|
1831
|
+
def write_mem(mem)
|
|
1832
|
+
mem_info = @mem_infos[mem]
|
|
1833
|
+
|
|
1834
|
+
unless mem_info
|
|
1835
|
+
puts "mem info not found delete mem"
|
|
1836
|
+
@writes.delete(mem)
|
|
1966
1837
|
return
|
|
1967
1838
|
end
|
|
1968
1839
|
|
|
1969
|
-
|
|
1970
|
-
data = mem_info[ :wbuff ]
|
|
1840
|
+
data = mem_info[:wbuff]
|
|
1971
1841
|
|
|
1972
|
-
if data.empty?
|
|
1973
|
-
@writes.delete(
|
|
1974
|
-
close_mem(
|
|
1842
|
+
if data.empty?
|
|
1843
|
+
@writes.delete(mem)
|
|
1844
|
+
close_mem(mem)
|
|
1975
1845
|
return
|
|
1976
1846
|
end
|
|
1977
1847
|
|
|
1978
1848
|
begin
|
|
1979
|
-
written = mem.write_nonblock(
|
|
1849
|
+
written = mem.write_nonblock(data)
|
|
1980
1850
|
rescue Errno::EINPROGRESS
|
|
1981
1851
|
return
|
|
1982
1852
|
rescue Exception => e
|
|
1983
|
-
close_mem(
|
|
1853
|
+
close_mem(mem)
|
|
1984
1854
|
return
|
|
1985
1855
|
end
|
|
1986
1856
|
|
|
1987
|
-
set_update(
|
|
1988
|
-
data = data[
|
|
1989
|
-
mem_info[
|
|
1857
|
+
set_update(mem)
|
|
1858
|
+
data = data[written..-1]
|
|
1859
|
+
mem_info[:wbuff] = data
|
|
1990
1860
|
end
|
|
1991
1861
|
|
|
1992
|
-
def write_p1(
|
|
1993
|
-
|
|
1994
|
-
|
|
1862
|
+
def write_p1(p1)
|
|
1863
|
+
p1_info = @p1_infos[p1]
|
|
1864
|
+
|
|
1865
|
+
unless p1_info
|
|
1866
|
+
puts "p1 info not found delete p1"
|
|
1867
|
+
@writes.delete(p1)
|
|
1995
1868
|
return
|
|
1996
1869
|
end
|
|
1997
1870
|
|
|
1998
|
-
p1_info =
|
|
1999
|
-
p1_info[
|
|
2000
|
-
data = p1_info[ :wbuff ]
|
|
1871
|
+
p1_info[:connected] = true
|
|
1872
|
+
data = p1_info[:wbuff]
|
|
2001
1873
|
|
|
2002
|
-
if data.empty?
|
|
2003
|
-
if p1_info[
|
|
2004
|
-
close_p1(
|
|
1874
|
+
if data.empty?
|
|
1875
|
+
if p1_info[:closing]
|
|
1876
|
+
close_p1(p1)
|
|
2005
1877
|
else
|
|
2006
|
-
@writes.delete(
|
|
1878
|
+
@writes.delete(p1)
|
|
2007
1879
|
end
|
|
2008
1880
|
|
|
2009
1881
|
return
|
|
2010
1882
|
end
|
|
2011
1883
|
|
|
2012
1884
|
begin
|
|
2013
|
-
written = p1.write_nonblock(
|
|
1885
|
+
written = p1.write_nonblock(data)
|
|
2014
1886
|
rescue Errno::EINPROGRESS
|
|
2015
1887
|
return
|
|
2016
1888
|
rescue Exception => e
|
|
2017
|
-
|
|
1889
|
+
puts "write p1 #{e.class}" if @is_debug
|
|
1890
|
+
close_p1(p1)
|
|
2018
1891
|
return
|
|
2019
1892
|
end
|
|
2020
1893
|
|
|
2021
|
-
set_update(
|
|
2022
|
-
data = data[
|
|
2023
|
-
p1_info[
|
|
2024
|
-
|
|
1894
|
+
set_update(p1)
|
|
1895
|
+
data = data[written..-1]
|
|
1896
|
+
p1_info[:wbuff] = data
|
|
1897
|
+
p2_id = p1_info[:p2_id]
|
|
2025
1898
|
|
|
2026
|
-
if p1_info[
|
|
2027
|
-
|
|
2028
|
-
|
|
2029
|
-
|
|
2030
|
-
|
|
2031
|
-
p1_info[ :overflowing ] = false
|
|
1899
|
+
if p1_info[:overflowing] && p1_info[:wbuff].empty?
|
|
1900
|
+
puts "p1 empty #{p2_id}"
|
|
1901
|
+
p1_info[:overflowing] = false
|
|
1902
|
+
puts "resume big"
|
|
1903
|
+
add_read(@big)
|
|
2032
1904
|
end
|
|
2033
1905
|
end
|
|
2034
1906
|
|
|
2035
|
-
def write_proxy(
|
|
2036
|
-
|
|
2037
|
-
|
|
1907
|
+
def write_proxy(proxy)
|
|
1908
|
+
proxy_info = @proxy_infos[proxy]
|
|
1909
|
+
|
|
1910
|
+
unless proxy_info
|
|
1911
|
+
puts "proxy info not found delete proxy"
|
|
1912
|
+
@writes.delete(proxy)
|
|
2038
1913
|
return
|
|
2039
1914
|
end
|
|
2040
1915
|
|
|
2041
|
-
|
|
2042
|
-
data = proxy_info[ :wbuff ]
|
|
1916
|
+
data = proxy_info[:wbuff]
|
|
2043
1917
|
|
|
2044
|
-
if data.empty?
|
|
2045
|
-
@writes.delete(
|
|
1918
|
+
if data.empty?
|
|
1919
|
+
@writes.delete(proxy)
|
|
2046
1920
|
return
|
|
2047
1921
|
end
|
|
2048
1922
|
|
|
2049
1923
|
begin
|
|
2050
|
-
if proxy_info[
|
|
2051
|
-
written = proxy.sendmsg_nonblock(
|
|
2052
|
-
proxy_info[
|
|
1924
|
+
if proxy_info[:is_syn]
|
|
1925
|
+
written = proxy.sendmsg_nonblock(data, 536870912, @proxyd_addr)
|
|
1926
|
+
proxy_info[:is_syn] = false
|
|
2053
1927
|
else
|
|
2054
|
-
written = proxy.write_nonblock(
|
|
1928
|
+
written = proxy.write_nonblock(data)
|
|
2055
1929
|
end
|
|
2056
1930
|
rescue Errno::EINPROGRESS
|
|
2057
1931
|
return
|
|
2058
1932
|
rescue Exception => e
|
|
2059
|
-
puts "write proxy #{
|
|
2060
|
-
close_proxy(
|
|
1933
|
+
puts "write proxy #{e.class}"
|
|
1934
|
+
close_proxy(proxy)
|
|
2061
1935
|
return
|
|
2062
1936
|
end
|
|
2063
1937
|
|
|
2064
|
-
set_update(
|
|
2065
|
-
data = data[
|
|
2066
|
-
proxy_info[
|
|
2067
|
-
bytesize = proxy_info[ :wbuff ].bytesize
|
|
2068
|
-
|
|
2069
|
-
if bytesize < RESUME_BELOW then
|
|
2070
|
-
if proxy_info[ :paused_srcs ].any? then
|
|
2071
|
-
puts "proxy underhalf resume srcs #{ proxy_info[ :paused_srcs ].size }"
|
|
2072
|
-
proxy_info[ :paused_srcs ].each{ | src | add_read( src ) }
|
|
2073
|
-
proxy_info[ :paused_srcs ].clear
|
|
2074
|
-
end
|
|
2075
|
-
|
|
2076
|
-
if proxy_info[ :paused_p1s ].any? then
|
|
2077
|
-
puts "proxy underhalf resume p1s #{ proxy_info[ :paused_p1s ].size }"
|
|
2078
|
-
proxy_info[ :paused_p1s ].each{ | p1 | add_read( p1 ) }
|
|
2079
|
-
proxy_info[ :paused_p1s ].clear
|
|
2080
|
-
end
|
|
2081
|
-
end
|
|
1938
|
+
set_update(proxy)
|
|
1939
|
+
data = data[written..-1]
|
|
1940
|
+
proxy_info[:wbuff] = data
|
|
2082
1941
|
end
|
|
2083
1942
|
|
|
2084
|
-
def write_src(
|
|
2085
|
-
|
|
2086
|
-
|
|
1943
|
+
def write_src(src)
|
|
1944
|
+
src_info = @src_infos[src]
|
|
1945
|
+
|
|
1946
|
+
unless src_info
|
|
1947
|
+
puts "src info not found delete src"
|
|
1948
|
+
@writes.delete(src)
|
|
2087
1949
|
return
|
|
2088
1950
|
end
|
|
2089
1951
|
|
|
2090
|
-
|
|
2091
|
-
data = src_info[ :wbuff ]
|
|
1952
|
+
data = src_info[:wbuff]
|
|
2092
1953
|
|
|
2093
|
-
if data.empty?
|
|
2094
|
-
if src_info[
|
|
2095
|
-
close_src(
|
|
1954
|
+
if data.empty?
|
|
1955
|
+
if src_info[:closing]
|
|
1956
|
+
close_src(src)
|
|
2096
1957
|
else
|
|
2097
|
-
@writes.delete(
|
|
1958
|
+
@writes.delete(src)
|
|
2098
1959
|
end
|
|
2099
1960
|
|
|
2100
1961
|
return
|
|
2101
1962
|
end
|
|
2102
1963
|
|
|
2103
1964
|
begin
|
|
2104
|
-
written = src.write_nonblock(
|
|
1965
|
+
written = src.write_nonblock(data)
|
|
2105
1966
|
rescue Errno::EINPROGRESS
|
|
2106
1967
|
return
|
|
2107
1968
|
rescue Exception => e
|
|
2108
|
-
|
|
1969
|
+
puts "write src #{e.class}" if @is_debug
|
|
1970
|
+
close_src(src)
|
|
2109
1971
|
return
|
|
2110
1972
|
end
|
|
2111
1973
|
|
|
2112
|
-
set_update(
|
|
2113
|
-
data = data[
|
|
2114
|
-
src_info[
|
|
2115
|
-
bytesize = src_info[ :wbuff ].bytesize
|
|
1974
|
+
set_update(src)
|
|
1975
|
+
data = data[written..-1]
|
|
1976
|
+
src_info[:wbuff] = data
|
|
2116
1977
|
|
|
2117
|
-
if src_info[
|
|
2118
|
-
|
|
2119
|
-
|
|
1978
|
+
if src_info[:wbuff].empty? && src_info[:overflowing]
|
|
1979
|
+
domain = src_info[:destination_domain]
|
|
1980
|
+
puts "src empty #{domain}"
|
|
1981
|
+
src_info[:overflowing] = false
|
|
2120
1982
|
|
|
2121
|
-
if src_info[
|
|
2122
|
-
puts "
|
|
2123
|
-
add_read(
|
|
1983
|
+
if src_info[:proxy_type] == :direct
|
|
1984
|
+
puts "resume dst"
|
|
1985
|
+
add_read(src_info[:dst])
|
|
2124
1986
|
else
|
|
2125
|
-
puts "
|
|
2126
|
-
|
|
2127
|
-
add_proxy_wbuff( pack_a_chunk( msg ) )
|
|
1987
|
+
puts "resume big"
|
|
1988
|
+
add_read(@big)
|
|
2128
1989
|
end
|
|
2129
|
-
|
|
2130
|
-
src_info[ :overflowing ] = false
|
|
2131
|
-
end
|
|
2132
|
-
end
|
|
2133
|
-
|
|
2134
|
-
def write_relay( relay )
|
|
2135
|
-
if relay.closed? then
|
|
2136
|
-
puts "write closed relay?"
|
|
2137
|
-
return
|
|
2138
|
-
end
|
|
2139
|
-
|
|
2140
|
-
relay_info = @relay_infos[ relay ]
|
|
2141
|
-
data = relay_info[ :wbuff ]
|
|
2142
|
-
|
|
2143
|
-
if data.empty? then
|
|
2144
|
-
if relay_info[ :closing ] then
|
|
2145
|
-
close_relay( relay )
|
|
2146
|
-
else
|
|
2147
|
-
@writes.delete( relay )
|
|
2148
|
-
end
|
|
2149
|
-
|
|
2150
|
-
return
|
|
2151
|
-
end
|
|
2152
|
-
|
|
2153
|
-
begin
|
|
2154
|
-
written = relay.write_nonblock( data )
|
|
2155
|
-
rescue Errno::EINPROGRESS
|
|
2156
|
-
return
|
|
2157
|
-
rescue Exception => e
|
|
2158
|
-
close_relay( relay )
|
|
2159
|
-
return
|
|
2160
|
-
end
|
|
2161
|
-
|
|
2162
|
-
set_update( relay )
|
|
2163
|
-
data = data[ written..-1 ]
|
|
2164
|
-
relay_info[ :wbuff ] = data
|
|
2165
|
-
bytesize = relay_info[ :wbuff ].bytesize
|
|
2166
|
-
|
|
2167
|
-
if relay_info[ :overflowing ] && ( bytesize < RESUME_BELOW ) then
|
|
2168
|
-
puts "relay underhalf"
|
|
2169
|
-
add_read( relay_info[ :girl ] )
|
|
2170
|
-
relay_info[ :overflowing ] = false
|
|
2171
1990
|
end
|
|
2172
1991
|
end
|
|
2173
1992
|
|