emonti-rbkb 0.6.2.1 → 0.6.6
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.
- data/History.txt +32 -0
- data/README.rdoc +10 -7
- data/Rakefile +47 -0
- data/bin/feed +5 -0
- data/bin/plugsrv +3 -3
- data/cli_usage.rdoc +44 -9
- data/doctor-bag.jpg +0 -0
- data/lib/rbkb.rb +47 -2
- data/lib/rbkb/cli.rb +8 -6
- data/lib/rbkb/cli/b64.rb +5 -0
- data/lib/rbkb/cli/bgrep.rb +14 -9
- data/lib/rbkb/cli/chars.rb +2 -1
- data/lib/rbkb/cli/crc32.rb +4 -1
- data/lib/rbkb/cli/d64.rb +3 -0
- data/lib/rbkb/cli/dedump.rb +5 -3
- data/lib/rbkb/cli/feed.rb +223 -0
- data/lib/rbkb/cli/hexify.rb +3 -3
- data/lib/rbkb/cli/len.rb +12 -9
- data/lib/rbkb/cli/rstrings.rb +13 -10
- data/lib/rbkb/cli/slice.rb +1 -0
- data/lib/rbkb/cli/telson.rb +21 -57
- data/lib/rbkb/cli/unhexify.rb +2 -6
- data/lib/rbkb/cli/urldec.rb +1 -0
- data/lib/rbkb/cli/urlenc.rb +1 -0
- data/lib/rbkb/extends.rb +41 -6
- data/lib/rbkb/http.rb +20 -0
- data/lib/rbkb/http/base.rb +172 -0
- data/lib/rbkb/http/body.rb +214 -0
- data/lib/rbkb/http/common.rb +74 -0
- data/lib/rbkb/http/headers.rb +356 -0
- data/lib/rbkb/http/parameters.rb +101 -0
- data/lib/rbkb/http/request.rb +58 -0
- data/lib/rbkb/http/response.rb +86 -0
- data/lib/rbkb/plug.rb +3 -3
- data/lib/rbkb/plug/cli.rb +83 -0
- data/lib/rbkb/plug/feed_import.rb +74 -0
- data/lib/rbkb/plug/plug.rb +36 -19
- data/lib/rbkb/plug/unix_domain.rb +75 -0
- data/rbkb.gemspec +38 -0
- data/spec/rbkb_spec.rb +7 -0
- data/spec/spec_helper.rb +16 -0
- data/tasks/ann.rake +80 -0
- data/tasks/bones.rake +20 -0
- data/tasks/gem.rake +201 -0
- data/tasks/git.rake +40 -0
- data/tasks/notes.rake +27 -0
- data/tasks/post_load.rake +34 -0
- data/tasks/rdoc.rake +51 -0
- data/tasks/rubyforge.rake +55 -0
- data/tasks/setup.rb +292 -0
- data/tasks/spec.rake +54 -0
- data/tasks/svn.rake +47 -0
- data/tasks/test.rake +40 -0
- data/test/test_cli_b64.rb +35 -0
- data/test/test_cli_bgrep.rb +137 -0
- data/test/test_cli_blit.rb +11 -0
- data/test/test_cli_chars.rb +21 -0
- data/test/test_cli_crc32.rb +108 -0
- data/test/test_cli_d64.rb +22 -0
- data/test/test_cli_dedump.rb +118 -0
- data/test/test_cli_feed.rb +11 -0
- data/test/test_cli_helper.rb +96 -0
- data/test/test_cli_hexify.rb +63 -0
- data/test/test_cli_len.rb +96 -0
- data/test/test_cli_rstrings.rb +15 -0
- data/test/test_cli_slice.rb +73 -0
- data/test/test_cli_telson.rb +11 -0
- data/test/test_cli_unhexify.rb +43 -0
- data/test/test_cli_urldec.rb +50 -0
- data/test/test_cli_urlenc.rb +44 -0
- data/test/test_cli_xor.rb +71 -0
- data/test/test_helper.rb +5 -0
- data/test/test_http.rb +27 -0
- data/test/test_http_helper.rb +60 -0
- data/test/test_http_request.rb +136 -0
- data/test/test_http_response.rb +222 -0
- data/test/test_rbkb.rb +19 -0
- metadata +127 -21
@@ -0,0 +1,58 @@
|
|
1
|
+
module Rbkb::Http
|
2
|
+
|
3
|
+
# A Request encapsulates all the entities in a HTTP request message
|
4
|
+
# including the action header, general headers, and body.
|
5
|
+
class Request < Base
|
6
|
+
attr_accessor :action
|
7
|
+
|
8
|
+
alias first_entity action
|
9
|
+
alias first_entity= action=
|
10
|
+
|
11
|
+
def request_parameters
|
12
|
+
@action.parameters
|
13
|
+
end
|
14
|
+
|
15
|
+
# Returns a new Headers object extended as RequestHeaders. This is the
|
16
|
+
# default object which will be used when composing fresh Request header
|
17
|
+
# entities.
|
18
|
+
def default_headers_obj(*args)
|
19
|
+
Headers.new(*args).extend(RequestHeaders)
|
20
|
+
end
|
21
|
+
|
22
|
+
# Returns a new BoundBody object. This is the default object which will
|
23
|
+
# be used when composing fresh Request body entities.
|
24
|
+
def default_body_obj(*args)
|
25
|
+
Body.new(*args)
|
26
|
+
end
|
27
|
+
|
28
|
+
# Returns a raw HTTP request for this instance. The instance must have
|
29
|
+
# an action element defined at the bare minimum.
|
30
|
+
def to_raw(tmp_body=@body)
|
31
|
+
raise "this request has no action entity" unless first_entity()
|
32
|
+
self.headers ||= default_headers_obj()
|
33
|
+
self.body ||= default_body_obj()
|
34
|
+
|
35
|
+
if len=@opts[:static_length]
|
36
|
+
@body = Body.new(@body, @body.opts) {|x| x.base = self}
|
37
|
+
@headers.set_header("Content-Length", len.to_i)
|
38
|
+
elsif @opts[:ignore_content_length]
|
39
|
+
@headers.delete_header("Content-Length")
|
40
|
+
end
|
41
|
+
|
42
|
+
bstr = tmp_body.to_raw
|
43
|
+
hdrs = (@headers).to_raw_array.unshift(first_entity.to_raw)
|
44
|
+
return "#{hdrs.join("\r\n")}\r\n\r\n#{bstr}"
|
45
|
+
end
|
46
|
+
|
47
|
+
|
48
|
+
# Parses a raw HTTP request and captures data into the current instance.
|
49
|
+
def capture(str)
|
50
|
+
raise "arg 0 must be a string" unless String === str
|
51
|
+
hstr, bstr = str.split(/\s*\r?\n\r?\n/, 2)
|
52
|
+
capture_headers(hstr)
|
53
|
+
self.body = content_length ? BoundBody.new : Body.new
|
54
|
+
capture_body(bstr)
|
55
|
+
return self
|
56
|
+
end
|
57
|
+
end
|
58
|
+
end
|
@@ -0,0 +1,86 @@
|
|
1
|
+
|
2
|
+
module Rbkb::Http
|
3
|
+
# A Response encapsulates all the entities in a HTTP response,
|
4
|
+
# including the status header, general headers, and body.
|
5
|
+
class Response < Base
|
6
|
+
attr_accessor :status
|
7
|
+
|
8
|
+
alias first_entity status
|
9
|
+
alias first_entity= status=
|
10
|
+
|
11
|
+
# Returns a raw HTTP response for this instance. Must have a status
|
12
|
+
# element defined at a bare minimum.
|
13
|
+
def to_raw(raw_body=nil)
|
14
|
+
raise "this response has no status" unless first_entity()
|
15
|
+
self.headers ||= default_headers_obj()
|
16
|
+
self.body = raw_body if raw_body
|
17
|
+
|
18
|
+
if do_chunked_encoding?(@headers)
|
19
|
+
unless @body.is_a? ChunkedBody
|
20
|
+
@body = ChunkedBody.new(@body, @body.opts)
|
21
|
+
end
|
22
|
+
@headers.delete_header("Content-Length")
|
23
|
+
elsif not opts[:ignore_content_length]
|
24
|
+
unless @body.is_a? BoundBody
|
25
|
+
@body = BoundBody.new(@body, @body.opts)
|
26
|
+
end
|
27
|
+
@headers.delete_header("Transfer-Encoding")
|
28
|
+
else
|
29
|
+
@body = Body.new(@body, @body.opts)
|
30
|
+
end
|
31
|
+
@body.base = self
|
32
|
+
|
33
|
+
yield(self) if block_given?
|
34
|
+
|
35
|
+
bstr = @body.to_raw
|
36
|
+
hdrs = @headers.to_raw_array.unshift(self.first_entity.to_raw)
|
37
|
+
return "#{hdrs.join("\r\n")}\r\n\r\n#{bstr}"
|
38
|
+
end
|
39
|
+
|
40
|
+
# Parses a raw HTTP response and captures data into the current instance.
|
41
|
+
def capture(str)
|
42
|
+
raise "arg 0 must be a string" unless String === str
|
43
|
+
hstr, bstr = str.split(/\s*\r?\n\r?\n/, 2)
|
44
|
+
|
45
|
+
capture_headers(hstr)
|
46
|
+
|
47
|
+
yield(self, bstr) if block_given?
|
48
|
+
|
49
|
+
unless @body and @body.capture_complete?
|
50
|
+
@body =
|
51
|
+
if do_chunked_encoding?
|
52
|
+
ChunkedBody.new {|b| b.base = self }
|
53
|
+
elsif content_length()
|
54
|
+
BoundBody.new {|b| b.base = self }
|
55
|
+
else
|
56
|
+
Body.new {|b| b.base = self }
|
57
|
+
end
|
58
|
+
end
|
59
|
+
|
60
|
+
capture_body(bstr)
|
61
|
+
|
62
|
+
return self
|
63
|
+
end
|
64
|
+
|
65
|
+
# Indicates whether to use chunked encoding based on presence of
|
66
|
+
# the "Transfer-Encoding: chunked" header or the :ignore_chunked_encoding
|
67
|
+
# opts parameter.
|
68
|
+
def do_chunked_encoding?(hdrs=@headers)
|
69
|
+
( (not @opts[:ignore_chunked_encoding]) and
|
70
|
+
(hdrs.get_header_value("Transfer-Encoding").first =~ /(?:^|\W)chunked(?:\W|$)/) )
|
71
|
+
end
|
72
|
+
|
73
|
+
# Returns a new Headers object extended as ResponseHeaders. This is the
|
74
|
+
# default object which will be used when composing fresh Response header
|
75
|
+
# entities.
|
76
|
+
def default_headers_obj(*args)
|
77
|
+
Headers.new(*args).extend(ResponseHeaders)
|
78
|
+
end
|
79
|
+
|
80
|
+
# Returns a new BoundBody object. This is the default object which will
|
81
|
+
# be used when composing fresh Response body entities.
|
82
|
+
def default_body_obj(*args)
|
83
|
+
BoundBody.new(*args)
|
84
|
+
end
|
85
|
+
end
|
86
|
+
end
|
data/lib/rbkb/plug.rb
CHANGED
@@ -0,0 +1,83 @@
|
|
1
|
+
require 'rbkb/cli'
|
2
|
+
require 'rbkb/plug'
|
3
|
+
require 'eventmachine'
|
4
|
+
|
5
|
+
|
6
|
+
# Copyright 2009 emonti at matasano.com
|
7
|
+
# See README.rdoc for license information
|
8
|
+
#
|
9
|
+
module Rbkb::Cli
|
10
|
+
|
11
|
+
# Rbkb::Cli::Executable is an abstract class for creating command line
|
12
|
+
# executables using the Ruby Black Bag framework.
|
13
|
+
class PlugCli < Executable
|
14
|
+
RX_HOST_AND_PORT = /^([\w\._-]+):(\d+)$/
|
15
|
+
RX_PORT_OPT_ADDR = /^(?:([\w\._-]+):)?(\d+)$/
|
16
|
+
|
17
|
+
attr_accessor :blit_addr, :blit_port, :blit_proto,
|
18
|
+
:local_addr, :local_port, :transport,
|
19
|
+
:target_addr, :target_port, :plug_opts
|
20
|
+
|
21
|
+
def initialize(*args)
|
22
|
+
super(*args) do |this|
|
23
|
+
this.blit_addr ||= Plug::Blit::DEFAULT_IPADDR
|
24
|
+
this.blit_port ||= Plug::Blit::DEFAULT_PORT
|
25
|
+
this.transport ||= :TCP
|
26
|
+
this.plug_opts ||= {}
|
27
|
+
yield this if block_given?
|
28
|
+
end
|
29
|
+
|
30
|
+
# TODO Plug::UI obviously need fixing.
|
31
|
+
# TODO It shouldn't be driven by constants for configuration
|
32
|
+
Plug::UI::LOGCFG[:verbose] = true
|
33
|
+
Plug::UI::LOGCFG[:dump] = :hex
|
34
|
+
Plug::UI::LOGCFG[:out] = @stderr
|
35
|
+
end
|
36
|
+
|
37
|
+
def make_parser()
|
38
|
+
arg = super()
|
39
|
+
arg.banner << " host:port"
|
40
|
+
|
41
|
+
arg.on("-o", "--output=FILE", "Output to file") do |o|
|
42
|
+
Plug::UI::LOGCFG[:out] = File.open(o, "w") # XXX
|
43
|
+
end
|
44
|
+
|
45
|
+
arg.on("-q", "--quiet", "Turn off verbose logging") do
|
46
|
+
Plug::UI::LOGCFG[:verbose] = false # XXX
|
47
|
+
end
|
48
|
+
|
49
|
+
arg.on("-d", "--dump-format=hex/raw",
|
50
|
+
"Output conversations in hexdump or raw") do |d|
|
51
|
+
if m=/^(hex|raw)$/i.match(d)
|
52
|
+
Plug::UI::LOGCFG[:dump] = m[1].downcase.to_sym # XXX
|
53
|
+
else
|
54
|
+
bail "Invalid dump format: #{d.inspect}"
|
55
|
+
end
|
56
|
+
end
|
57
|
+
|
58
|
+
arg.on("-b", "--blit=ADDR:PORT", "Where to listen for blit") do |b|
|
59
|
+
unless m=RX_PORT_OPT_ADDR.match(b)
|
60
|
+
bail("Invalid blit address/port")
|
61
|
+
end
|
62
|
+
@blit_port = m[2].to_i
|
63
|
+
@blit_addr = m[1] if m[1]
|
64
|
+
end
|
65
|
+
|
66
|
+
arg.on("-u", "--udp", "UDP mode") { @transport=:UDP }
|
67
|
+
|
68
|
+
arg.on("-S", "--start-tls", "Initiate TLS") {|s| @plug_opts[:tls]=true }
|
69
|
+
|
70
|
+
return arg
|
71
|
+
end
|
72
|
+
|
73
|
+
def parse_target_argument()
|
74
|
+
unless (m = RX_HOST_AND_PORT.match(tgt=@argv.shift))
|
75
|
+
bail "Invalid target: #{tgt}\n Hint: use -h"
|
76
|
+
end
|
77
|
+
@target_addr = m[1]
|
78
|
+
@target_port = m[2].to_i
|
79
|
+
return m
|
80
|
+
end
|
81
|
+
end
|
82
|
+
end
|
83
|
+
|
@@ -0,0 +1,74 @@
|
|
1
|
+
# Copyright 2009 emonti at matasano.com
|
2
|
+
# See README.rdoc for license information
|
3
|
+
#
|
4
|
+
|
5
|
+
require 'yaml'
|
6
|
+
require 'rbkb'
|
7
|
+
|
8
|
+
module FeedImport
|
9
|
+
|
10
|
+
## TODO switch to pcaprub or some other up to date pcap lib. make it a dep.
|
11
|
+
begin
|
12
|
+
## This requires the 'ruby-pcap' library from:
|
13
|
+
## http://raa.ruby-lang.org/project/pcap/
|
14
|
+
## ... which is old and krufty...
|
15
|
+
$VERBOSE=nil
|
16
|
+
require 'pcaplet'
|
17
|
+
$VERBOSE=false
|
18
|
+
|
19
|
+
# Imports an array from pcap
|
20
|
+
def import_pcap(file, filter=nil)
|
21
|
+
ret = Array.new
|
22
|
+
pcap = Pcap::Capture.open_offline(file)
|
23
|
+
pcap.setfilter filter if filter
|
24
|
+
pcap.each_packet do |pkt|
|
25
|
+
if ( (pkt.udp? and dat=pkt.udp_data) or
|
26
|
+
(pkt.tcp? and dat=pkt.tcp_data and not dat.empty?)
|
27
|
+
)
|
28
|
+
ret << dat
|
29
|
+
end
|
30
|
+
end
|
31
|
+
return ret
|
32
|
+
end
|
33
|
+
rescue LoadError
|
34
|
+
def import_pcap(*args)
|
35
|
+
raise "you must install ruby-pcap to use this feature"
|
36
|
+
end
|
37
|
+
end
|
38
|
+
|
39
|
+
module_function :import_pcap
|
40
|
+
|
41
|
+
|
42
|
+
# Imports an array from yaml
|
43
|
+
def import_yaml(file)
|
44
|
+
unless ( ret = YAML.load_file(file) ).kind_of? Array
|
45
|
+
raise "#{file.inspect} did not provide an array"
|
46
|
+
end
|
47
|
+
return ret
|
48
|
+
end
|
49
|
+
module_function :import_yaml
|
50
|
+
|
51
|
+
|
52
|
+
# Imports from hexdumps separated by "%" and merged by ','
|
53
|
+
def import_dump(file)
|
54
|
+
ret = []
|
55
|
+
dat = File.read(file)
|
56
|
+
dat.strip.split(/^%$/).each do |msg|
|
57
|
+
ret << ""
|
58
|
+
msg.strip.split(/^,$/).each do |chunk|
|
59
|
+
ret[-1] << chunk.strip.dehexdump
|
60
|
+
end
|
61
|
+
end
|
62
|
+
return ret
|
63
|
+
end
|
64
|
+
module_function :import_dump
|
65
|
+
|
66
|
+
# Imports raw messages in files by a glob pattern (i.e. /tmp/foo/msgs.*)
|
67
|
+
# Manage filenames so that they're in the right order on import.
|
68
|
+
# See Dir.glob for valid globbing patterns.
|
69
|
+
def import_rawfiles(glob_pat)
|
70
|
+
Dir.glob(glob_pat).map { |f| File.read(f) }
|
71
|
+
end
|
72
|
+
module_function :import_rawfiles
|
73
|
+
end
|
74
|
+
|
data/lib/rbkb/plug/plug.rb
CHANGED
@@ -21,21 +21,37 @@ module Plug
|
|
21
21
|
|
22
22
|
def self.dump(from, to, dat)
|
23
23
|
if dump=LOGCFG[:dump]
|
24
|
-
LOGCFG[:out].puts "%% #{from} SAYS TO #{to} LEN=#{dat.size}"
|
25
|
-
|
26
|
-
|
24
|
+
LOGCFG[:out].puts "%% #{from} SAYS TO #{to} LEN=#{dat.size}" if LOGCFG[:verbose]
|
25
|
+
case dump
|
26
|
+
when :hex
|
27
|
+
dat.hexdump(:out => LOGCFG[:out])
|
28
|
+
when :raw
|
29
|
+
LOGCFG[:out].puts dat
|
30
|
+
else
|
31
|
+
LOGCFG[:out].puts dat
|
32
|
+
end
|
33
|
+
LOGCFG[:out].puts "%%" if LOGCFG[:verbose]
|
27
34
|
end
|
28
35
|
end
|
29
36
|
end
|
30
37
|
|
31
38
|
|
32
39
|
module Base
|
33
|
-
attr_accessor :peers, :transport, :kind
|
40
|
+
attr_accessor :peers, :transport, :kind, :tls, :tls_opts, :no_stop_on_unbind
|
34
41
|
|
35
|
-
def initialize(transport)
|
42
|
+
def initialize(transport, opts={})
|
36
43
|
# raise "Invalid transport #{transport.inspect}" unless (:UDP, :TCP).include?(transport)
|
37
44
|
@transport = transport
|
38
45
|
@peers = PeerList.new(self)
|
46
|
+
|
47
|
+
opts.each_pair do |k,v|
|
48
|
+
accessor = k.to_s + "="
|
49
|
+
if self.respond_to?(accessor)
|
50
|
+
self.send(accessor, v)
|
51
|
+
else
|
52
|
+
raise "Bad attribute: #{k}"
|
53
|
+
end
|
54
|
+
end
|
39
55
|
end
|
40
56
|
|
41
57
|
def name
|
@@ -81,6 +97,9 @@ module Plug
|
|
81
97
|
UI.verbose "** #{name} Started"
|
82
98
|
if @kind==:server and peer=plug_peer
|
83
99
|
UI.log "** #{name} CONNECTED TO #{peer.name}"
|
100
|
+
if tls
|
101
|
+
start_tls(tls_opts || {})
|
102
|
+
end
|
84
103
|
end
|
85
104
|
end
|
86
105
|
|
@@ -94,12 +113,18 @@ module Plug
|
|
94
113
|
def connection_completed
|
95
114
|
peer = plug_peer
|
96
115
|
UI.log "** #{name} CONNECTED TO #{peer.name}"
|
116
|
+
if tls
|
117
|
+
start_tls(tls_opts || {})
|
118
|
+
end
|
97
119
|
return peer
|
98
120
|
end
|
99
121
|
|
100
122
|
def unbind
|
101
123
|
UI.log "** Connection " + ((@peers.empty?)? "refused." : "closed.")
|
102
|
-
|
124
|
+
unless @no_stop_on_unbind
|
125
|
+
UI.log "STOPPING!!"
|
126
|
+
EM.stop
|
127
|
+
end
|
103
128
|
end
|
104
129
|
end
|
105
130
|
|
@@ -137,21 +162,13 @@ module Plug
|
|
137
162
|
attr_accessor :pos, :feed, :step, :close_at_end, :go_first,
|
138
163
|
:squelch_exhausted
|
139
164
|
|
140
|
-
def initialize(
|
141
|
-
super(
|
165
|
+
def initialize(*args)
|
166
|
+
super(*args)
|
142
167
|
|
143
|
-
@pos
|
144
|
-
@feed
|
168
|
+
@pos ||= 0
|
169
|
+
@feed ||= []
|
145
170
|
|
146
|
-
|
147
|
-
accessor = k.to_s + "="
|
148
|
-
if self.respond_to?(accessor)
|
149
|
-
self.send(accessor, v)
|
150
|
-
else
|
151
|
-
raise "Bad attribute: #{k}"
|
152
|
-
end
|
153
|
-
end
|
154
|
-
raise "feed must be enumerable" unless @feed.kind_of? Enumerable
|
171
|
+
raise "feed must be enumerable" unless Enumerable === @feed
|
155
172
|
end
|
156
173
|
|
157
174
|
def go
|
@@ -0,0 +1,75 @@
|
|
1
|
+
# Copyright 2009 emonti at matasano.com
|
2
|
+
# See README.rdoc for license information
|
3
|
+
#
|
4
|
+
|
5
|
+
# Experimental!!!
|
6
|
+
|
7
|
+
require 'eventmachine'
|
8
|
+
require 'rbkb/plug'
|
9
|
+
require 'rbkb'
|
10
|
+
|
11
|
+
module Plug
|
12
|
+
class PeerStub
|
13
|
+
attr_reader :owner
|
14
|
+
|
15
|
+
def initialize(owner)
|
16
|
+
@owner = owner
|
17
|
+
end
|
18
|
+
|
19
|
+
def [](junk)
|
20
|
+
@owner
|
21
|
+
end
|
22
|
+
|
23
|
+
def []=(junk)
|
24
|
+
[@owner]
|
25
|
+
end
|
26
|
+
|
27
|
+
def peers
|
28
|
+
nil
|
29
|
+
end
|
30
|
+
end
|
31
|
+
|
32
|
+
module UnixDomain
|
33
|
+
attr_accessor :mute, :peers
|
34
|
+
|
35
|
+
def initialize
|
36
|
+
@peers = PeerStub.new(self)
|
37
|
+
end
|
38
|
+
|
39
|
+
def name
|
40
|
+
"a domain socket"
|
41
|
+
end
|
42
|
+
|
43
|
+
def receive_data(dat)
|
44
|
+
puts "Got:", dat.hexdump
|
45
|
+
end
|
46
|
+
|
47
|
+
def say(dat, sender)
|
48
|
+
UI.dump(sender.name, self.name, dat)
|
49
|
+
send_data(dat)
|
50
|
+
end
|
51
|
+
end
|
52
|
+
end
|
53
|
+
|
54
|
+
|
55
|
+
if $0 == __FILE__
|
56
|
+
Plug::UI::LOGCFG[:verbose] = true
|
57
|
+
|
58
|
+
b_addr = Plug::Blit::DEFAULT_IPADDR
|
59
|
+
b_port = Plug::Blit::DEFAULT_PORT
|
60
|
+
unless (sock=ARGV.shift and ARGV.shift.nil?)
|
61
|
+
STDERR.puts "usage: #{File.basename $0} unix_socket"
|
62
|
+
exit 1
|
63
|
+
end
|
64
|
+
|
65
|
+
|
66
|
+
EventMachine.run {
|
67
|
+
s = EventMachine.connect_unix_domain(sock, Plug::UnixDomain)
|
68
|
+
Plug::UI::verbose("** UNIX-DOMAIN-#{sock.inspect} Started")
|
69
|
+
|
70
|
+
# connect a blit channel:
|
71
|
+
EventMachine.start_server(b_addr, b_port, Plug::Blit, :TCP, s)
|
72
|
+
Plug::UI::verbose("** BLITSRV-#{b_addr}:#{b_port}(TCP) Started")
|
73
|
+
}
|
74
|
+
|
75
|
+
end
|