girl 0.95.0 → 1.0.0

This diff has not been reviewed by any users.
Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 995e842429be7063ce5e29248927b336029f2e4dc864e4855979770d18ff7766
4
- data.tar.gz: 83b4619a2b8cf5f99058282345478eee57a2b7638cefafa5a15d1d0170abfb96
3
+ metadata.gz: 0c0254d6f9509721f13f14148087071820ae5ad13a3a7a87884d5372e7d93035
4
+ data.tar.gz: 2e718e248d7b3967e350a0dd4b6266c2a396a7eb5193a2fcd419222606b9ac19
5
5
  SHA512:
6
- metadata.gz: 349a7012c29fd90bae97816b1af481d25623f580969f3ec354c0b747c43aea805bba0b02f8ebb8e653427b12fa5af07584fc3566ddb67bd48fd04947b4386fcf
7
- data.tar.gz: c078531bb08ed0568e28170336c2a10b8b22896b2138bfdc149d9f61758cae938816ea623f7b4e7bab89e48620c855c731c4c3fdb2485573f2706125e9602b7c
6
+ metadata.gz: f9546abfd9b420cf80fa128670ba0db60e95bf54ed88466e1309820bb247ced3e7aa552d6afb93db12388a35b3d432d6994dfe2ea9a5f80580c82dce8655ff66
7
+ data.tar.gz: 7e3b2c573cd03bb284cc5d51a44b0c4aa882f7c069759f63075216759cf5abdab44f80babe5f3dbe81c126a05d9e1449c9e65bab0d34e3a9f184a417e922d326
@@ -25,8 +25,6 @@ lib/girl/proxy.rb
25
25
  lib/girl/proxyd_custom.rb
26
26
  lib/girl/proxyd_worker.rb
27
27
  lib/girl/proxyd.rb
28
- lib/girl/udp.rb
29
- lib/girl/udpd.rb
30
28
  lib/girl/version.rb
31
29
  ]
32
30
 
@@ -13,6 +13,13 @@ module Girl
13
13
  @mutex = Mutex.new
14
14
  @reads = []
15
15
  @writes = []
16
+ @closing_srcs = []
17
+ @paused_srcs = []
18
+ @paused_dsts = []
19
+ @paused_streams = []
20
+ @resume_srcs = []
21
+ @resume_dsts = []
22
+ @resume_streams = []
16
23
  @roles = {} # sock => :dotr / :proxy / :src / :dst / :tun / :stream
17
24
  @src_infos = {} # src => {}
18
25
  @dst_infos = {} # dst => {}
@@ -37,7 +44,6 @@ module Girl
37
44
  rs, ws = IO.select( @reads, @writes )
38
45
 
39
46
  @mutex.synchronize do
40
- # 先读,再写,避免打上关闭标记后读到
41
47
  rs.each do | sock |
42
48
  case @roles[ sock ]
43
49
  when :dotr then
@@ -90,6 +96,15 @@ module Girl
90
96
 
91
97
  private
92
98
 
99
+ ##
100
+ # add closing src
101
+ #
102
+ def add_closing_src( src )
103
+ return if src.closed? || @closing_srcs.include?( src )
104
+ @closing_srcs << src
105
+ next_tick
106
+ end
107
+
93
108
  ##
94
109
  # add ctlmsg
95
110
  #
@@ -101,14 +116,56 @@ module Girl
101
116
  if to_addr then
102
117
  @tun_info[ :ctlmsgs ] << [ data, to_addr ]
103
118
  add_write( @tun )
119
+ next_tick
104
120
  end
105
121
  end
106
122
 
123
+ ##
124
+ # add dst wbuff
125
+ #
126
+ def add_dst_wbuff( dst, data )
127
+ dst_info = @dst_infos[ dst ]
128
+ dst_info[ :wbuff ] << data
129
+ add_write( dst )
130
+
131
+ if dst_info[ :wbuff ].bytesize >= WBUFF_LIMIT then
132
+ puts "p#{ Process.pid } #{ Time.new } pause direct src #{ dst_info[ :domain ] }"
133
+ add_paused_src( dst_info[ :src ] )
134
+ end
135
+ end
136
+
137
+ ##
138
+ # add paused dst
139
+ #
140
+ def add_paused_dst( dst )
141
+ return if dst.closed? || @paused_dsts.include?( dst )
142
+ @reads.delete( dst )
143
+ @paused_dsts << dst
144
+ end
145
+
146
+ ##
147
+ # add paused src
148
+ #
149
+ def add_paused_src( src )
150
+ return if src.closed? || @paused_srcs.include?( src )
151
+ @reads.delete( src )
152
+ @paused_srcs << src
153
+ end
154
+
155
+ ##
156
+ # add paused stream
157
+ #
158
+ def add_paused_stream( stream )
159
+ return if stream.closed? || @paused_streams.include?( stream )
160
+ @reads.delete( stream )
161
+ @paused_streams << stream
162
+ end
163
+
107
164
  ##
108
165
  # add read
109
166
  #
110
167
  def add_read( sock, role = nil )
111
- unless @reads.include?( sock ) then
168
+ if !sock.closed? && !@reads.include?( sock ) then
112
169
  @reads << sock
113
170
 
114
171
  if role then
@@ -117,11 +174,51 @@ module Girl
117
174
  end
118
175
  end
119
176
 
177
+ ##
178
+ # add resume dst
179
+ #
180
+ def add_resume_dst( dst )
181
+ return if @resume_dsts.include?( dst )
182
+ @resume_dsts << dst
183
+ next_tick
184
+ end
185
+
186
+ ##
187
+ # add resume src
188
+ #
189
+ def add_resume_src( src )
190
+ return if @resume_srcs.include?( src )
191
+ @resume_srcs << src
192
+ next_tick
193
+ end
194
+
195
+ ##
196
+ # add resume stream
197
+ #
198
+ def add_resume_stream( stream )
199
+ return if @resume_streams.include?( stream )
200
+ @resume_streams << stream
201
+ next_tick
202
+ end
203
+
204
+ ##
205
+ # add src rbuff
206
+ #
207
+ def add_src_rbuff( src, data )
208
+ src_info = @src_infos[ src ]
209
+ src_info[ :rbuff ] << data
210
+
211
+ if src_info[ :rbuff ].bytesize >= WBUFF_LIMIT then
212
+ # puts "debug1 src.rbuff full"
213
+ add_closing_src( src )
214
+ end
215
+ end
216
+
120
217
  ##
121
218
  # add src wbuff
122
219
  #
123
220
  def add_src_wbuff( src, data )
124
- return if src.closed?
221
+ return if src.closed? || @closing_srcs.include?( src )
125
222
  src_info = @src_infos[ src ]
126
223
  src_info[ :wbuff ] << data
127
224
  src_info[ :last_recv_at ] = Time.new
@@ -131,18 +228,14 @@ module Girl
131
228
  dst = src_info[ :dst ]
132
229
 
133
230
  if dst then
134
- dst_info = @dst_infos[ dst ]
135
- puts "p#{ Process.pid } #{ Time.new } pause dst #{ dst_info[ :domain ] }"
136
- dst_info[ :paused ] = true
137
- @reads.delete( dst )
231
+ puts "p#{ Process.pid } #{ Time.new } pause dst #{ src_info[ :destination_domain ] }"
232
+ add_paused_dst( dst )
138
233
  else
139
234
  stream = src_info[ :stream ]
140
235
 
141
236
  if stream then
142
- stream_info = @stream_infos[ stream ]
143
- puts "p#{ Process.pid } #{ Time.new } pause stream #{ stream_info[ :domain ] }"
144
- stream_info[ :paused ] = true
145
- @reads.delete( stream )
237
+ puts "p#{ Process.pid } #{ Time.new } pause stream #{ src_info[ :destination_domain ] }"
238
+ add_paused_stream( stream )
146
239
  end
147
240
  end
148
241
  end
@@ -164,34 +257,46 @@ module Girl
164
257
  end
165
258
 
166
259
  ##
167
- # add write
260
+ # add stream wbuff
168
261
  #
169
- def add_write( sock )
170
- unless @writes.include?( sock ) then
171
- @writes << sock
262
+ def add_stream_wbuff( stream, data )
263
+ stream_info = @stream_infos[ stream ]
264
+ stream_info[ :wbuff ] << data
265
+ add_write( stream )
266
+
267
+ if stream_info[ :wbuff ].bytesize >= WBUFF_LIMIT then
268
+ puts "p#{ Process.pid } #{ Time.new } pause tunnel src #{ stream_info[ :domain ] }"
269
+ add_paused_src( stream_info[ :src ] )
172
270
  end
173
271
  end
174
272
 
175
273
  ##
176
- # close sock
274
+ # add write
177
275
  #
178
- def close_sock( sock )
179
- sock.close
180
- @reads.delete( sock )
181
- @writes.delete( sock )
182
- @roles.delete( sock )
276
+ def add_write( sock )
277
+ if !sock.closed? && !@writes.include?( sock ) then
278
+ @writes << sock
279
+ end
183
280
  end
184
281
 
185
282
  ##
186
- # close dst
283
+ # close read dst
187
284
  #
188
- def close_dst( dst )
189
- # puts "debug1 close dst"
190
- close_sock( dst )
191
- dst_info = @dst_infos.delete( dst )
192
- src = dst_info[ :src ]
193
- close_read_src( src )
194
- set_src_closing_write( src )
285
+ def close_read_dst( dst )
286
+ return if dst.closed?
287
+ # puts "debug1 close read dst"
288
+ dst.close_read
289
+ @reads.delete( dst )
290
+
291
+ if dst.closed? then
292
+ # puts "debug1 delete dst info"
293
+ @roles.delete( dst )
294
+ dst_info = @dst_infos.delete( dst )
295
+ else
296
+ dst_info = @dst_infos[ dst ]
297
+ end
298
+
299
+ dst_info
195
300
  end
196
301
 
197
302
  ##
@@ -211,30 +316,9 @@ module Girl
211
316
  src_info = @src_infos[ src ]
212
317
  end
213
318
 
214
- src_info[ :paused ] = false
215
319
  src_info
216
320
  end
217
321
 
218
- ##
219
- # close read dst
220
- #
221
- def close_read_dst( dst )
222
- return if dst.closed?
223
- # puts "debug1 close read dst"
224
- dst.close_read
225
- @reads.delete( dst )
226
-
227
- if dst.closed? then
228
- # puts "debug1 delete dst info"
229
- @roles.delete( dst )
230
- dst_info = @dst_infos.delete( dst )
231
- else
232
- dst_info = @dst_infos[ dst ]
233
- end
234
-
235
- dst_info
236
- end
237
-
238
322
  ##
239
323
  # close read stream
240
324
  #
@@ -255,68 +339,47 @@ module Girl
255
339
  stream_info
256
340
  end
257
341
 
342
+ ##
343
+ # close sock
344
+ #
345
+ def close_sock( sock )
346
+ sock.close
347
+ @reads.delete( sock )
348
+ @writes.delete( sock )
349
+ @roles.delete( sock )
350
+ end
351
+
258
352
  ##
259
353
  # close src
260
354
  #
261
355
  def close_src( src )
356
+ return if src.closed?
262
357
  # puts "debug1 close src"
263
358
  close_sock( src )
264
359
  src_info = del_src_info( src )
265
360
  dst = src_info[ :dst ]
266
361
 
267
362
  if dst then
268
- close_read_dst( dst )
269
- set_dst_closing_write( dst )
363
+ close_sock( dst )
364
+ @dst_infos.delete( dst )
270
365
  else
271
366
  stream = src_info[ :stream ]
272
367
 
273
368
  if stream then
274
- close_read_stream( stream )
275
- set_stream_closing_write( stream )
369
+ close_sock( stream )
370
+ @stream_infos.delete( stream )
276
371
  end
277
372
  end
278
373
  end
279
374
 
280
- ##
281
- # close stream
282
- #
283
- def close_stream( stream )
284
- # puts "debug1 close stream"
285
- close_sock( stream )
286
- stream_info = @stream_infos.delete( stream )
287
- src = stream_info[ :src ]
288
- close_read_src( src )
289
- set_src_closing_write( src )
290
- end
291
-
292
375
  ##
293
376
  # close tun
294
377
  #
295
378
  def close_tun( tun )
296
379
  # puts "debug1 close tun"
297
380
  close_sock( tun )
298
- @tun_info[ :srcs ].each{ | _, src | set_src_closing( src ) }
299
- end
300
-
301
- ##
302
- # close write src
303
- #
304
- def close_write_src( src )
305
- return if src.closed?
306
- # puts "debug1 close write src"
307
- src.close_write
308
- @writes.delete( src )
309
-
310
- if src.closed? then
311
- # puts "debug1 delete src info"
312
- @roles.delete( src )
313
- src_info = del_src_info( src )
314
- else
315
- src_info = @src_infos[ src ]
316
- end
317
-
318
- src_info[ :closed_write ] = true
319
- src_info
381
+ @tun_info[ :ctlmsgs ].clear
382
+ @tun_info[ :srcs ].each{ | _, src | close_src( src ) }
320
383
  end
321
384
 
322
385
  ##
@@ -336,10 +399,29 @@ module Girl
336
399
  dst_info = @dst_infos[ dst ]
337
400
  end
338
401
 
339
- dst_info[ :closed_write ] = true
340
402
  dst_info
341
403
  end
342
404
 
405
+ ##
406
+ # close write src
407
+ #
408
+ def close_write_src( src )
409
+ return if src.closed?
410
+ # puts "debug1 close write src"
411
+ src.close_write
412
+ @writes.delete( src )
413
+
414
+ if src.closed? then
415
+ # puts "debug1 delete src info"
416
+ @roles.delete( src )
417
+ src_info = del_src_info( src )
418
+ else
419
+ src_info = @src_infos[ src ]
420
+ end
421
+
422
+ src_info
423
+ end
424
+
343
425
  ##
344
426
  # close write stream
345
427
  #
@@ -357,7 +439,6 @@ module Girl
357
439
  stream_info = @stream_infos[ stream ]
358
440
  end
359
441
 
360
- stream_info[ :closed_write ] = true
361
442
  stream_info
362
443
  end
363
444
 
@@ -384,7 +465,7 @@ module Girl
384
465
  def del_src_info( src )
385
466
  src_info = @src_infos.delete( src )
386
467
 
387
- if ( src_info[ :proxy_type ] == :tunnel ) && @tun && !@tun.closed? then
468
+ if ( src_info[ :proxy_type ] == :tunnel ) && @tun then
388
469
  @tun_info[ :srcs ].delete( src_info[ :id ] )
389
470
  end
390
471
 
@@ -400,7 +481,6 @@ module Girl
400
481
  sleep CHECK_EXPIRE_INTERVAL
401
482
 
402
483
  @mutex.synchronize do
403
- trigger = false
404
484
  now = Time.new
405
485
 
406
486
  if @tun && !@tun.closed? then
@@ -414,8 +494,6 @@ module Girl
414
494
  data = [ 0, HEARTBEAT ].pack( 'Q>C' )
415
495
  add_ctlmsg( data )
416
496
  end
417
-
418
- trigger = true
419
497
  end
420
498
 
421
499
  @src_infos.each do | src, src_info |
@@ -424,12 +502,9 @@ module Girl
424
502
 
425
503
  if ( now - last_recv_at >= EXPIRE_AFTER ) && ( now - last_sent_at >= EXPIRE_AFTER ) then
426
504
  puts "p#{ Process.pid } #{ Time.new } expire src #{ src_info[ :destination_domain ] }"
427
- set_src_closing( src )
428
- trigger = true
505
+ add_closing_src( src )
429
506
  end
430
507
  end
431
-
432
- next_tick if trigger
433
508
  end
434
509
  end
435
510
  end
@@ -444,56 +519,61 @@ module Girl
444
519
  sleep CHECK_RESUME_INTERVAL
445
520
 
446
521
  @mutex.synchronize do
447
- trigger = false
448
-
449
- @src_infos.select{ | _, src_info | src_info[ :paused ] }.each do | src, src_info |
450
- dst = src_info[ :dst ]
451
-
452
- if dst then
453
- dst_info = @dst_infos[ dst ]
454
-
455
- if dst_info[ :wbuff ].size < RESUME_BELOW then
456
- puts "p#{ Process.pid } #{ Time.new } dst.wbuff below #{ RESUME_BELOW }, resume src #{ src_info[ :destination_domain ] }"
457
- resume_src( src )
458
- trigger = true
459
- end
522
+ @paused_srcs.each do | src |
523
+ if src.closed? then
524
+ add_resume_src( src )
460
525
  else
461
- stream = src_info[ :stream ]
462
- stream_info = @stream_infos[ stream ]
463
-
464
- if stream_info[ :wbuff ].size < RESUME_BELOW then
465
- puts "p#{ Process.pid } #{ Time.new } stream.wbuff below #{ RESUME_BELOW }, resume src #{ src_info[ :destination_domain ] }"
466
- resume_src( src )
467
- trigger = true
526
+ src_info = @src_infos[ src ]
527
+ dst = src_info[ :dst ]
528
+
529
+ if dst then
530
+ dst_info = @dst_infos[ dst ]
531
+
532
+ if dst_info[ :wbuff ].size < RESUME_BELOW then
533
+ puts "p#{ Process.pid } #{ Time.new } resume direct src #{ src_info[ :destination_domain ] }"
534
+ add_resume_src( src )
535
+ end
536
+ else
537
+ stream = src_info[ :stream ]
538
+ stream_info = @stream_infos[ stream ]
539
+
540
+ if stream_info[ :wbuff ].size < RESUME_BELOW then
541
+ puts "p#{ Process.pid } #{ Time.new } resume tunnel src #{ src_info[ :destination_domain ] }"
542
+ add_resume_src( src )
543
+ end
468
544
  end
469
545
  end
470
546
  end
471
547
 
472
- @dst_infos.select{ | _, dst_info | dst_info[ :paused ] }.each do | dst, dst_info |
473
- src = dst_info[ :src ]
474
- src_info = @src_infos[ src ]
548
+ @paused_dsts.each do | dst |
549
+ if dst.closed? then
550
+ add_resume_dst( dst )
551
+ else
552
+ dst_info = @dst_infos[ dst ]
553
+ src = dst_info[ :src ]
554
+ src_info = @src_infos[ src ]
475
555
 
476
- if src_info[ :wbuff ].size < RESUME_BELOW then
477
- puts "p#{ Process.pid } #{ Time.new } src.wbuff below #{ RESUME_BELOW }, resume dst #{ dst_info[ :domain ] }"
478
- dst_info[ :paused ] = false
479
- add_read( dst )
480
- trigger = true
556
+ if src_info[ :wbuff ].size < RESUME_BELOW then
557
+ puts "p#{ Process.pid } #{ Time.new } resume dst #{ dst_info[ :domain ] }"
558
+ add_resume_dst( dst )
559
+ end
481
560
  end
482
561
  end
483
562
 
484
- @stream_infos.select{ | _, stream_info | stream_info[ :paused ] }.each do | stream, stream_info |
485
- src = stream_info[ :src ]
486
- src_info = @src_infos[ src ]
563
+ @paused_streams.each do | stream |
564
+ if stream.closed? then
565
+ add_resume_stream( stream )
566
+ else
567
+ stream_info = @stream_infos[ stream ]
568
+ src = stream_info[ :src ]
569
+ src_info = @src_infos[ src ]
487
570
 
488
- if src_info[ :wbuff ].size < RESUME_BELOW then
489
- puts "p#{ Process.pid } #{ Time.new } src.wbuff below #{ RESUME_BELOW }, resume stream #{ stream_info[ :domain ] }"
490
- stream_info[ :paused ] = false
491
- add_read( stream )
492
- trigger = true
571
+ if src_info[ :wbuff ].size < RESUME_BELOW then
572
+ puts "p#{ Process.pid } #{ Time.new } resume stream #{ stream_info[ :domain ] }"
573
+ add_resume_stream( stream )
574
+ end
493
575
  end
494
576
  end
495
-
496
- next_tick if trigger
497
577
  end
498
578
  end
499
579
  end
@@ -513,7 +593,7 @@ module Girl
513
593
 
514
594
  Thread.new do
515
595
  SEND_HELLO_COUNT.times do | i |
516
- if @tun.nil? || @tun.closed? || src.closed? || src_info[ :stream ] then
596
+ if @tun.nil? || @tun.closed? || @tun_info[ :closing ] || src.closed? || src_info[ :stream ] then
517
597
  # puts "debug1 break loop send a new source #{ src_info[ :dst_port ] }"
518
598
  break
519
599
  end
@@ -524,7 +604,6 @@ module Girl
524
604
  end
525
605
 
526
606
  add_ctlmsg( data )
527
- next_tick
528
607
  end
529
608
 
530
609
  sleep SEND_HELLO_INTERVAL
@@ -549,21 +628,17 @@ module Girl
549
628
  # connect nonblock 必抛 wait writable
550
629
  rescue Exception => e
551
630
  puts "p#{ Process.pid } #{ Time.new } dst connect destination #{ domain } #{ src_info[ :destination_port ] } #{ ip_info.ip_address } #{ e.class }, close src"
552
- set_src_closing( src )
631
+ dst.close
632
+ add_closing_src( src )
553
633
  return
554
634
  end
555
635
 
556
636
  # puts "debug1 a new dst #{ dst.local_address.inspect }"
557
- local_port = dst.local_address.ip_port
558
637
  dst_info = {
559
- local_port: local_port, # 本地端口
560
- src: src, # 对应src
561
- domain: domain, # 目的地
562
- wbuff: '', # 写前,从src读到的流量
563
- paused: false, # 是否已暂停读
564
- closing: false, # 准备关闭
565
- closing_write: false, # 准备关闭写
566
- closed_write: false # 已关闭写
638
+ src: src, # 对应src
639
+ domain: domain, # 目的地
640
+ wbuff: '', # 写前,从src读到的流量
641
+ closing_write: false # 准备关闭写
567
642
  }
568
643
 
569
644
  @dst_infos[ dst ] = dst_info
@@ -585,6 +660,25 @@ module Girl
585
660
  end
586
661
  end
587
662
 
663
+ ##
664
+ # new a proxy
665
+ #
666
+ def new_a_proxy( proxy_port )
667
+ proxy = Socket.new( Socket::AF_INET, Socket::SOCK_STREAM, 0 )
668
+ proxy.setsockopt( Socket::SOL_SOCKET, Socket::SO_REUSEADDR, 1 )
669
+
670
+ if RUBY_PLATFORM.include?( 'linux' ) then
671
+ proxy.setsockopt( Socket::SOL_SOCKET, Socket::SO_REUSEPORT, 1 )
672
+ proxy.setsockopt( Socket::SOL_TCP, Socket::TCP_NODELAY, 1 )
673
+ end
674
+
675
+ proxy.bind( Socket.sockaddr_in( proxy_port, '0.0.0.0' ) )
676
+ proxy.listen( 127 )
677
+ puts "p#{ Process.pid } #{ Time.new } proxy listen on #{ proxy_port }"
678
+ add_read( proxy, :proxy )
679
+ @proxy_local_address = proxy.local_address
680
+ end
681
+
588
682
  ##
589
683
  # new a stream
590
684
  #
@@ -597,7 +691,7 @@ module Girl
597
691
 
598
692
  if dst_id == 0 then
599
693
  puts "p#{ Process.pid } #{ Time.new } remote dst already closed"
600
- set_src_closing( src )
694
+ add_closing_src( src )
601
695
  return
602
696
  end
603
697
 
@@ -609,6 +703,7 @@ module Girl
609
703
  rescue IO::WaitWritable
610
704
  rescue Exception => e
611
705
  puts "p#{ Process.pid } #{ Time.new } connect tcpd #{ e.class }"
706
+ stream.close
612
707
  return
613
708
  end
614
709
 
@@ -625,10 +720,7 @@ module Girl
625
720
  src: src, # 对应src
626
721
  domain: domain, # 目的地
627
722
  wbuff: data, # 写前,写往远端streamd
628
- paused: false, # 是否已暂停读
629
- closing: false, # 准备关闭
630
- closing_write: false, # 准备关闭写
631
- closed_write: false # 已关闭写
723
+ closing_write: false # 准备关闭写
632
724
  }
633
725
 
634
726
  src_info[ :dst_id ] = dst_id
@@ -646,25 +738,6 @@ module Girl
646
738
  end
647
739
  end
648
740
 
649
- ##
650
- # new a proxy
651
- #
652
- def new_a_proxy( proxy_port )
653
- proxy = Socket.new( Socket::AF_INET, Socket::SOCK_STREAM, 0 )
654
- proxy.setsockopt( Socket::SOL_SOCKET, Socket::SO_REUSEADDR, 1 )
655
-
656
- if RUBY_PLATFORM.include?( 'linux' ) then
657
- proxy.setsockopt( Socket::SOL_SOCKET, Socket::SO_REUSEPORT, 1 )
658
- proxy.setsockopt( Socket::SOL_TCP, Socket::TCP_NODELAY, 1 )
659
- end
660
-
661
- proxy.bind( Socket.sockaddr_in( proxy_port, '0.0.0.0' ) )
662
- proxy.listen( 127 )
663
- puts "p#{ Process.pid } #{ Time.new } proxy listen on #{ proxy_port }"
664
- add_read( proxy, :proxy )
665
- @proxy_local_address = proxy.local_address
666
- end
667
-
668
741
  ##
669
742
  # new a tun
670
743
  #
@@ -692,7 +765,7 @@ module Girl
692
765
 
693
766
  Thread.new do
694
767
  SEND_HELLO_COUNT.times do | i |
695
- if @tun.nil? || @tun.closed? || @tun_info[ :tund_addr ] then
768
+ if @tun.nil? || @tun.closed? || @tun_info[ :closing ] || @tun_info[ :tund_addr ] then
696
769
  # puts "debug1 break loop send hello"
697
770
  break
698
771
  end
@@ -703,7 +776,6 @@ module Girl
703
776
  # puts "debug1 #{ data.inspect }"
704
777
 
705
778
  add_ctlmsg( data, @proxyd_addr )
706
- next_tick
707
779
  end
708
780
 
709
781
  sleep SEND_HELLO_INTERVAL
@@ -723,7 +795,7 @@ module Girl
723
795
  #
724
796
  def resolve_domain( src, domain )
725
797
  if @remotes.any? { | remote | ( domain.size >= remote.size ) && ( domain[ ( remote.size * -1 )..-1 ] == remote ) } then
726
- # puts "debug1 #{ domain } hit remotes"
798
+ puts "p#{ Process.pid } #{ Time.new } #{ domain } hit remotes"
727
799
  set_src_proxy_type_tunnel( src )
728
800
  return
729
801
  end
@@ -760,41 +832,15 @@ module Girl
760
832
  unless src.closed? then
761
833
  puts "p#{ Process.pid } #{ Time.new } resolved #{ domain } #{ ip_info.ip_address }"
762
834
  deal_with_destination_ip( src, ip_info )
835
+ next_tick
763
836
  end
764
837
  else
765
- set_src_closing( src )
838
+ add_closing_src( src )
766
839
  end
767
-
768
- next_tick
769
840
  end
770
841
  end
771
842
  end
772
843
 
773
- ##
774
- # resume src
775
- #
776
- def resume_src( src )
777
- src_info = @src_infos[ src ]
778
- src_info[ :paused ] = false
779
- add_read( src )
780
- end
781
-
782
- ##
783
- # set dst closing
784
- #
785
- def set_dst_closing( dst )
786
- return if dst.closed?
787
- dst_info = @dst_infos[ dst ]
788
- dst_info[ :closing ] = true
789
-
790
- if dst_info[ :closed_write ] then
791
- add_read( dst )
792
- else
793
- @reads.delete( dst )
794
- add_write( dst )
795
- end
796
- end
797
-
798
844
  ##
799
845
  # set dst closing write
800
846
  #
@@ -802,36 +848,20 @@ module Girl
802
848
  return if dst.closed?
803
849
 
804
850
  dst_info = @dst_infos[ dst ]
805
- return if dst_info[ :closed_write ]
851
+ return if dst_info[ :closing_write ]
806
852
 
807
853
  dst_info[ :closing_write ] = true
808
854
  add_write( dst )
809
855
  end
810
856
 
811
- ##
812
- # set src is closing
813
- #
814
- def set_src_closing( src )
815
- return if src.closed?
816
- src_info = @src_infos[ src ]
817
- src_info[ :closing ] = true
818
-
819
- if src_info[ :closed_write ] then
820
- add_read( src )
821
- else
822
- @reads.delete( src )
823
- add_write( src )
824
- end
825
- end
826
-
827
857
  ##
828
858
  # set src closing write
829
859
  #
830
860
  def set_src_closing_write( src )
831
- return if src.closed?
861
+ return if src.closed? || @closing_srcs.include?( src )
832
862
 
833
863
  src_info = @src_infos[ src ]
834
- return if src_info[ :closed_write ]
864
+ return if src_info[ :closing_write ]
835
865
 
836
866
  src_info[ :closing_write ] = true
837
867
  add_write( src )
@@ -841,10 +871,6 @@ module Girl
841
871
  # set src proxy type tunnel
842
872
  #
843
873
  def set_src_proxy_type_tunnel( src )
844
- if @tun.nil? || @tun.closed? then
845
- new_a_tun
846
- end
847
-
848
874
  src_info = @src_infos[ src ]
849
875
  src_info[ :proxy_type ] = :tunnel
850
876
  src_id = src_info[ :id ]
@@ -864,7 +890,7 @@ module Girl
864
890
  return if stream.closed?
865
891
 
866
892
  stream_info = @stream_infos[ stream ]
867
- return if stream_info[ :closed_write ]
893
+ return if stream_info[ :closing_write ]
868
894
 
869
895
  stream_info[ :closing_write ] = true
870
896
  add_write( stream )
@@ -874,10 +900,11 @@ module Girl
874
900
  # set tun is closing
875
901
  #
876
902
  def set_tun_closing
877
- return if @tun.closed?
903
+ return if @tun.closed? || @tun_info[ :closing ]
878
904
  @tun_info[ :closing ] = true
879
905
  @reads.delete( @tun )
880
- add_write( @tun )
906
+ @writes.delete( @tun )
907
+ next_tick
881
908
  end
882
909
 
883
910
  ##
@@ -903,7 +930,43 @@ module Girl
903
930
  # read dotr
904
931
  #
905
932
  def read_dotr( dotr )
906
- dotr.read( 1 )
933
+ dotr.read_nonblock( READ_SIZE )
934
+
935
+ if @tun && !@tun.closed? && @tun_info[ :closing ] then
936
+ close_tun( @tun )
937
+ end
938
+
939
+ if @closing_srcs.any? then
940
+ @closing_srcs.each{ | src | close_src( src ) }
941
+ @closing_srcs.clear
942
+ end
943
+
944
+ if @resume_srcs.any? then
945
+ @resume_srcs.each do | src |
946
+ add_read( src )
947
+ @paused_srcs.delete( src )
948
+ end
949
+
950
+ @resume_srcs.clear
951
+ end
952
+
953
+ if @resume_dsts.any? then
954
+ @resume_dsts.each do | dst |
955
+ add_read( dst )
956
+ @paused_dsts.delete( dst )
957
+ end
958
+
959
+ @resume_dsts.clear
960
+ end
961
+
962
+ if @resume_streams.any? then
963
+ @resume_streams.each do | stream |
964
+ add_read( stream )
965
+ @paused_streams.delete( stream )
966
+ end
967
+
968
+ @resume_streams.clear
969
+ end
907
970
  end
908
971
 
909
972
  ##
@@ -935,19 +998,23 @@ module Girl
935
998
  created_at: Time.new, # 创建时间
936
999
  last_recv_at: nil, # 上一次收到新流量(由dst收到,或者由stream收到)的时间
937
1000
  last_sent_at: nil, # 上一次发出流量(由dst发出,或者由stream发出)的时间
938
- paused: false, # 是否已暂停读
939
- closing: false, # 准备关闭
940
- closing_write: false, # 准备关闭写
941
- closed_write: false # 已关闭写
1001
+ closing_write: false # 准备关闭写
942
1002
  }
943
1003
 
944
1004
  add_read( src, :src )
1005
+
1006
+ # 用到tun,是在解析目的地域名得出是国外ip之后。但解析域名是额外的线程,为避免多线程重复建tun,在accept到src时就建。
1007
+ if @tun.nil? || @tun.closed? then
1008
+ new_a_tun
1009
+ end
945
1010
  end
946
1011
 
947
1012
  ##
948
1013
  # read tun
949
1014
  #
950
1015
  def read_tun( tun )
1016
+ return if tun.closed?
1017
+
951
1018
  begin
952
1019
  data, addrinfo, rflags, *controls = tun.recvmsg_nonblock
953
1020
  rescue IO::WaitReadable, Errno::EINTR
@@ -1028,13 +1095,6 @@ module Girl
1028
1095
  end
1029
1096
 
1030
1097
  src_info = @src_infos[ src ]
1031
-
1032
- # 处理关闭
1033
- if src_info[ :closing ] then
1034
- close_src( src )
1035
- return
1036
- end
1037
-
1038
1098
  proxy_type = src_info[ :proxy_type ]
1039
1099
 
1040
1100
  case proxy_type
@@ -1045,7 +1105,7 @@ module Girl
1045
1105
 
1046
1106
  unless domain_port then
1047
1107
  puts "p#{ Process.pid } #{ Time.new } CONNECT miss domain"
1048
- set_src_closing( src )
1108
+ add_closing_src( src )
1049
1109
  return
1050
1110
  end
1051
1111
  elsif data[ 0 ].unpack( 'C' ).first == 5 then
@@ -1063,7 +1123,7 @@ module Girl
1063
1123
 
1064
1124
  unless methods.include?( 0 ) then
1065
1125
  puts "p#{ Process.pid } #{ Time.new } miss method 00"
1066
- set_src_closing( src )
1126
+ add_closing_src( src )
1067
1127
  return
1068
1128
  end
1069
1129
 
@@ -1083,7 +1143,7 @@ module Girl
1083
1143
 
1084
1144
  unless host_line then
1085
1145
  # puts "debug1 not found host line"
1086
- set_src_closing( src )
1146
+ add_closing_src( src )
1087
1147
  return
1088
1148
  end
1089
1149
 
@@ -1095,7 +1155,7 @@ module Girl
1095
1155
 
1096
1156
  unless domain_port then
1097
1157
  puts "p#{ Process.pid } #{ Time.new } Host line miss domain"
1098
- set_src_closing( src )
1158
+ add_closing_src( src )
1099
1159
  return
1100
1160
  end
1101
1161
  end
@@ -1160,26 +1220,13 @@ module Girl
1160
1220
  data, _ = sub_http_request( data )
1161
1221
  end
1162
1222
 
1163
- stream_info = @stream_infos[ stream ]
1164
1223
  data = @custom.encode( data )
1165
1224
  # puts "debug2 add stream.wbuff encoded #{ data.bytesize }"
1166
- stream_info[ :wbuff ] << data
1167
- add_write( stream )
1168
-
1169
- if stream_info[ :wbuff ].bytesize >= WBUFF_LIMIT then
1170
- puts "p#{ Process.pid } #{ Time.new } pause tunnel src #{ src_info[ :destination_domain ] }"
1171
- src_info[ :paused ] = true
1172
- @reads.delete( src )
1173
- end
1225
+ add_stream_wbuff( stream, data )
1174
1226
  end
1175
1227
  else
1176
1228
  # puts "debug1 stream not ready, save data to src.rbuff"
1177
- src_info[ :rbuff ] << data
1178
-
1179
- if src_info[ :rbuff ].bytesize >= WBUFF_LIMIT then
1180
- # puts "debug1 tunnel src.rbuff full"
1181
- set_src_closing( src )
1182
- end
1229
+ add_src_rbuff( src, data )
1183
1230
  end
1184
1231
  when :direct then
1185
1232
  dst = src_info[ :dst ]
@@ -1190,25 +1237,12 @@ module Girl
1190
1237
  data, _ = sub_http_request( data )
1191
1238
  end
1192
1239
 
1193
- dst_info = @dst_infos[ dst ]
1194
1240
  # puts "debug2 add dst.wbuff #{ data.bytesize }"
1195
- dst_info[ :wbuff ] << data
1196
- add_write( dst )
1197
-
1198
- if dst_info[ :wbuff ].bytesize >= WBUFF_LIMIT then
1199
- puts "p#{ Process.pid } #{ Time.new } pause direct src #{ src_info[ :destination_domain ] }"
1200
- src_info[ :paused ] = true
1201
- @reads.delete( src )
1202
- end
1241
+ add_dst_wbuff( dst, data )
1203
1242
  end
1204
1243
  else
1205
1244
  # puts "debug1 dst not ready, save data to src.rbuff"
1206
- src_info[ :rbuff ] << data
1207
-
1208
- if src_info[ :rbuff ].bytesize >= WBUFF_LIMIT then
1209
- # puts "debug1 direct src.rbuff full"
1210
- set_src_closing( src )
1211
- end
1245
+ add_src_rbuff( src, data )
1212
1246
  end
1213
1247
  end
1214
1248
  end
@@ -1233,13 +1267,6 @@ module Girl
1233
1267
  end
1234
1268
 
1235
1269
  dst_info = @dst_infos[ dst ]
1236
-
1237
- # 处理关闭
1238
- if dst_info[ :closing ] then
1239
- close_dst( dst )
1240
- return
1241
- end
1242
-
1243
1270
  src = dst_info[ :src ]
1244
1271
  add_src_wbuff( src, data )
1245
1272
  end
@@ -1274,13 +1301,7 @@ module Girl
1274
1301
  # write tun
1275
1302
  #
1276
1303
  def write_tun( tun )
1277
- # 处理关闭
1278
- if @tun_info[ :closing ] then
1279
- close_tun( tun )
1280
- return
1281
- end
1282
-
1283
- now = Time.new
1304
+ return if tun.closed?
1284
1305
 
1285
1306
  # 发ctlmsg
1286
1307
  while @tun_info[ :ctlmsgs ].any? do
@@ -1292,8 +1313,8 @@ module Girl
1292
1313
  puts "p#{ Process.pid } #{ Time.new } wait send ctlmsg, left #{ @tun_info[ :ctlmsgs ].size }"
1293
1314
  return
1294
1315
  rescue Errno::EHOSTUNREACH, Errno::ENETUNREACH, Errno::ENETDOWN => e
1295
- puts "p#{ Process.pid } #{ Time.new } sendmsg #{ e.class }, close tun"
1296
- close_tun( tun )
1316
+ puts "p#{ Process.pid } #{ Time.new } sendmsg #{ e.class }, set tun closing"
1317
+ set_tun_closing
1297
1318
  return
1298
1319
  end
1299
1320
 
@@ -1310,14 +1331,6 @@ module Girl
1310
1331
  return if src.closed?
1311
1332
  src_info = @src_infos[ src ]
1312
1333
  dst = src_info[ :dst ]
1313
-
1314
- # 处理关闭
1315
- if src_info[ :closing ] then
1316
- close_src( src )
1317
- return
1318
- end
1319
-
1320
- # 处理wbuff
1321
1334
  data = src_info[ :wbuff ]
1322
1335
 
1323
1336
  # 写前为空,处理关闭写
@@ -1363,13 +1376,6 @@ module Girl
1363
1376
  return if dst.closed?
1364
1377
  dst_info = @dst_infos[ dst ]
1365
1378
  src = dst_info[ :src ]
1366
-
1367
- # 处理关闭
1368
- if dst_info[ :closing ] then
1369
- close_dst( dst )
1370
- return
1371
- end
1372
-
1373
1379
  data = dst_info[ :wbuff ]
1374
1380
 
1375
1381
  # 写前为空,处理关闭写
@@ -1412,13 +1418,6 @@ module Girl
1412
1418
  return if stream.closed?
1413
1419
  stream_info = @stream_infos[ stream ]
1414
1420
  src = stream_info[ :src ]
1415
-
1416
- # 处理关闭
1417
- if stream_info[ :closing ] then
1418
- close_stream( stream )
1419
- return
1420
- end
1421
-
1422
1421
  data = stream_info[ :wbuff ]
1423
1422
 
1424
1423
  # 写前为空,处理关闭写