midori.rb 0.6.0 → 0.7.0

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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: ccffda67e06a88ed46a9e81ac52823498d331a147869f54a3c520bc70946f469
4
- data.tar.gz: 2abeba1e323655b28a547814eccc536773b35316075b3852897ec109b4272719
3
+ metadata.gz: f6d14d7e6c7a05f01d72029dc8d09ad83c37328d392d8c745b938025181d9812
4
+ data.tar.gz: dc2d8754f72ff25354f33fd0a15a0e23a1617eaa4a82ec94b21f9e47b2ed5eda
5
5
  SHA512:
6
- metadata.gz: d68c112f68c228a79b46f2983e0bd4ba9b0ff25b8aa9025eca7893909719e7213a8236fca26d78ba2aad12926481d7f989d920148e00b866f9f86c8a6b3cff20
7
- data.tar.gz: 6eae1c01af1fa93acf6bf817ce1c04121918a53d1f849815778eed0f974c36259bd1ee6df3901b86128d247b77dfca5c81e04e5e1477836aa2dd31c0c2a1061e
6
+ metadata.gz: 0f4bf5b25cb38d3f5b8cf2a8f685956086d920ccc9cee3c838cc1fc3a94c1e482576f193d4d6c03505104b32d403a959da924e7243105f87b5faebc5d2d17b3e
7
+ data.tar.gz: cc1e70247c020875415d73e2bba4190c9f33c3ad52dacff0574eb89b5a6f3e1ee2c68efbbd330e4af83e9b86270d64fb26ac27133a30a8ebe68ed0cbbfbffd07
@@ -1,32 +1,58 @@
1
1
  #include <ruby.h>
2
+ #include <ruby/encoding.h>
2
3
 
3
4
  VALUE Midori = Qnil;
4
5
  VALUE MidoriWebSocket = Qnil;
5
6
 
6
7
  void Init_midori_ext();
7
8
  VALUE method_midori_websocket_mask(VALUE self, VALUE payload, VALUE mask);
9
+ VALUE method_midori_websocket_mask_str(VALUE self, VALUE payload, VALUE mask);
8
10
 
9
- void Init_midori_ext() {
11
+ void Init_midori_ext()
12
+ {
10
13
  Midori = rb_define_module("Midori");
11
14
  MidoriWebSocket = rb_define_class_under(Midori, "WebSocket", rb_cObject);
12
15
  rb_define_protected_method(MidoriWebSocket, "mask", method_midori_websocket_mask, 2);
16
+ rb_define_protected_method(MidoriWebSocket, "mask_str", method_midori_websocket_mask_str, 2);
13
17
  }
14
18
 
15
- VALUE method_midori_websocket_mask(VALUE self, VALUE payload, VALUE mask) {
19
+ VALUE method_midori_websocket_mask(VALUE self, VALUE payload, VALUE mask)
20
+ {
16
21
  long n = RARRAY_LEN(payload), i, p, m;
17
22
  VALUE unmasked = rb_ary_new2(n);
18
23
 
19
24
  int mask_array[] = {
20
- NUM2INT(rb_ary_entry(mask, 0)),
21
- NUM2INT(rb_ary_entry(mask, 1)),
22
- NUM2INT(rb_ary_entry(mask, 2)),
23
- NUM2INT(rb_ary_entry(mask, 3))
24
- };
25
+ NUM2INT(rb_ary_entry(mask, 0)),
26
+ NUM2INT(rb_ary_entry(mask, 1)),
27
+ NUM2INT(rb_ary_entry(mask, 2)),
28
+ NUM2INT(rb_ary_entry(mask, 3))};
25
29
 
26
- for (i = 0; i < n; i++) {
30
+ for (i = 0; i < n; i++)
31
+ {
27
32
  p = NUM2INT(rb_ary_entry(payload, i));
28
33
  m = mask_array[i % 4];
29
34
  rb_ary_store(unmasked, i, INT2NUM(p ^ m));
30
35
  }
31
36
  return unmasked;
32
37
  }
38
+
39
+ VALUE method_midori_websocket_mask_str(VALUE self, VALUE payload, VALUE mask)
40
+ {
41
+ long n = RARRAY_LEN(payload), i, p, m;
42
+ char result[n];
43
+
44
+ int mask_array[] = {
45
+ NUM2INT(rb_ary_entry(mask, 0)),
46
+ NUM2INT(rb_ary_entry(mask, 1)),
47
+ NUM2INT(rb_ary_entry(mask, 2)),
48
+ NUM2INT(rb_ary_entry(mask, 3))};
49
+
50
+ for (i = 0; i < n; i++)
51
+ {
52
+ p = NUM2INT(rb_ary_entry(payload, i));
53
+ m = mask_array[i % 4];
54
+ result[i] = p ^ m;
55
+ }
56
+
57
+ return rb_enc_str_new(result, n, rb_utf8_encoding());
58
+ }
data/lib/midori.rb CHANGED
@@ -13,8 +13,8 @@ require_relative 'midori/core_ext/configurable'
13
13
  require_relative 'midori/core_ext/define_class'
14
14
  require_relative 'midori/core_ext/http_header'
15
15
  require_relative 'midori/core_ext/proc'
16
+ require_relative 'midori/core_ext/socket'
16
17
  require_relative 'midori/core_ext/string'
17
- require_relative 'midori/core_ext/tcp_server'
18
18
 
19
19
  require_relative 'midori/version'
20
20
 
@@ -13,6 +13,7 @@ class Midori::Configure
13
13
  set :trusted_proxies, /\A127\.0\.0\.1\Z|\A(10|172\.(1[6-9]|2[0-9]|30|31)|192\.168)\.|
14
14
  \A::1\Z|\Afd[0-9a-f]{2}:.+|\Alocalhost\Z|\Aunix\Z|\Aunix:/ix
15
15
  set :tcp_fast_open, true
16
+ set :socket_reuse_port, false
16
17
  set :keep_alive, true
17
18
  set :keep_alive_timeout, 75
18
19
  set :keep_alive_requests, 1000
@@ -11,15 +11,16 @@ class Midori::Connection
11
11
  # @param [IO] socket raw socket
12
12
  def initialize(socket)
13
13
  @registered = false
14
- @socket = socket
14
+ @socket = socket[0]
15
+ @peer_addr = socket[1].ip_unpack
15
16
  @monitor = nil
16
17
  @close_flag = false
17
18
  @buffer = ''
18
- listen(socket)
19
+ listen(@socket)
19
20
  end
20
21
 
21
22
  # Register events of connection
22
- # @param [IO] socket raw socket
23
+ # @param [Array] socket raw socket
23
24
  def listen(socket)
24
25
  EventLoop.register(socket, :rw) do |monitor|
25
26
  @monitor = monitor
@@ -1,9 +1,16 @@
1
- class TCPServer
1
+ class Socket
2
2
  def tcp_fast_open
3
3
  # macOS devices option is DIFFERENT from Linux and FreeBSD
4
4
  opt = (/darwin/ =~ RUBY_PLATFORM) ? 1 : 5
5
5
  # Magic number 6 may refer to Socket::SOL_TCP or Socket::IPPROTO_TCP
6
- self.setsockopt(6, Socket::TCP_FASTOPEN, opt)
6
+ setsockopt(6, Socket::TCP_FASTOPEN, opt)
7
+ true
8
+ rescue => _e
9
+ false
10
+ end
11
+
12
+ def reuse_port
13
+ setsockopt(Socket::SOL_SOCKET, Socket::SO_REUSEPORT, 1)
7
14
  true
8
15
  rescue => _e
9
16
  false
data/lib/midori/runner.rb CHANGED
@@ -30,9 +30,7 @@ class Midori::Runner
30
30
  def start
31
31
  return false if running? || EventLoop.running?
32
32
  @logger.info "Midori #{Midori::VERSION} is now running on #{bind}:#{port}".blue
33
- @server = TCPServer.new(@bind, @port)
34
- tfo = @server.tcp_fast_open if Midori::Configure.tcp_fast_open
35
- @logger.warn 'Failed to use TCP Fast Open feature on your OS'.yellow unless tfo
33
+ init_socket
36
34
  async_fiber(Fiber.new do
37
35
  @logger.info 'Midori is booting...'.blue
38
36
  @before.call
@@ -47,6 +45,17 @@ class Midori::Runner
47
45
  nil
48
46
  end
49
47
 
48
+ private def init_socket
49
+ @server = Socket.new Socket::AF_INET, Socket::SOCK_STREAM
50
+ @server.reuse_port if Midori::Configure.socket_reuse_port
51
+ @server.bind Addrinfo.tcp @bind, @port
52
+ @server.listen Socket::SOMAXCONN
53
+ if Midori::Configure.tcp_fast_open
54
+ tfo = @server.tcp_fast_open
55
+ @logger.warn 'Failed to use TCP Fast Open feature on your OS'.yellow unless tfo
56
+ end
57
+ end
58
+
50
59
  # Stop the Midori server
51
60
  # @note This is an async method, but no callback
52
61
  # @return [Boolean] [true] stop successfully
data/lib/midori/server.rb CHANGED
@@ -32,8 +32,7 @@ module Midori::Server
32
32
  def receive_data(monitor)
33
33
  async_fiber(Fiber.new do
34
34
  begin
35
- _sock_domain, remote_port, _remote_hostname, remote_ip = monitor.io.peeraddr
36
- @request.ip, @request.port = remote_port, remote_ip
35
+ @request.ip, @request.port = @peer_addr
37
36
  data = monitor.io.read_nonblock(16_384)
38
37
  if @request.parsed? && @request.body_parsed?
39
38
  websocket_request(StringIO.new(data))
@@ -1,5 +1,5 @@
1
1
  # Midori Module
2
2
  module Midori
3
3
  # Current Version Code
4
- VERSION = '0.6.0'.freeze
4
+ VERSION = '0.7.0'.freeze
5
5
  end
@@ -24,7 +24,7 @@ class Midori::WebSocket
24
24
  @opcode = byte_tmp & 0b00001111
25
25
  # NOT Support Multiple Fragments
26
26
  raise Midori::Exception::ContinuousFrame unless fin
27
- raise Midori::Exception::OpCodeError unless [0x1, 0x2, 0x8, 0x9, 0xA].include? opcode
27
+ raise Midori::Exception::OpCodeError unless [0x1, 0x2, 0x8, 0x9, 0xA].include? @opcode
28
28
  close if @opcode == 0x8 # Close Frame
29
29
  # return if @opcode == 0x9 || @opcode == 0xA # Ping Pong
30
30
  decode_mask(data)
@@ -42,8 +42,11 @@ class Midori::WebSocket
42
42
  mask = Array.new(4) { data.getbyte }
43
43
  # Message
44
44
  masked_msg = Array.new(payload) { data.getbyte }
45
- @msg = self.mask(masked_msg, mask)
46
- @msg = @msg.pack('C*').force_encoding('utf-8') if [0x1, 0x9, 0xA].include? opcode
45
+ if [0x1, 0x9, 0xA].include? opcode
46
+ @msg = mask_str(masked_msg, mask)
47
+ else # [0x2]
48
+ @msg = mask(masked_msg, mask)
49
+ end
47
50
  # For debug
48
51
  # data.rewind
49
52
  # data.bytes {|byte| puts byte.to_s(16)}
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: midori.rb
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.6.0
4
+ version: 0.7.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - HeckPsi Lab
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2018-06-29 00:00:00.000000000 Z
11
+ date: 2018-07-10 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: murasaki
@@ -91,8 +91,8 @@ files:
91
91
  - lib/midori/core_ext/define_class.rb
92
92
  - lib/midori/core_ext/http_header.rb
93
93
  - lib/midori/core_ext/proc.rb
94
+ - lib/midori/core_ext/socket.rb
94
95
  - lib/midori/core_ext/string.rb
95
- - lib/midori/core_ext/tcp_server.rb
96
96
  - lib/midori/env.rb
97
97
  - lib/midori/eventsource.rb
98
98
  - lib/midori/exception.rb
@@ -133,7 +133,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
133
133
  version: '0'
134
134
  requirements: []
135
135
  rubyforge_project:
136
- rubygems_version: 2.7.6
136
+ rubygems_version: 2.7.7
137
137
  signing_key:
138
138
  specification_version: 4
139
139
  summary: High performance ruby web framework