tortard 0.0.1
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/README.md +28 -0
- data/bin/tortard +18 -0
- data/lib/tortard.rb +78 -0
- data/lib/tortard/address.rb +32 -0
- data/lib/tortard/bridge.rb +49 -0
- data/lib/tortard/bridge/client.rb +66 -0
- data/lib/tortard/bridge/connection.rb +45 -0
- data/lib/tortard/map.rb +30 -0
- data/lib/tortard/utils.rb +17 -0
- data/tortard.gemspec +17 -0
- metadata +87 -0
data/README.md
ADDED
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
tortard - tor for tards
|
|
2
|
+
=======================
|
|
3
|
+
Just a simple app to map SOCKS address and port to a local address and port that doesn't require
|
|
4
|
+
SOCKS.
|
|
5
|
+
|
|
6
|
+
```ruby
|
|
7
|
+
# this will map port 80 of silkroadvb5piz3r.onion to port 9433 on localhost
|
|
8
|
+
host 'silkroadvb5piz3r.onion' do
|
|
9
|
+
map 80, 'localhost:9433'
|
|
10
|
+
end
|
|
11
|
+
|
|
12
|
+
# you can achieve the same with
|
|
13
|
+
map 'silkroadvb5piz3r.onion:80', 'localhost:9433'
|
|
14
|
+
|
|
15
|
+
# if you want you can use SSL
|
|
16
|
+
ssl :internal do
|
|
17
|
+
# maps here will use SSL internally, which means you will be able to connect
|
|
18
|
+
# to the local port without SSL
|
|
19
|
+
end
|
|
20
|
+
|
|
21
|
+
ssl :external do
|
|
22
|
+
# this will require SSL to connect but won't use it internally
|
|
23
|
+
end
|
|
24
|
+
|
|
25
|
+
ssl :both do
|
|
26
|
+
# this will use SSL on both ends
|
|
27
|
+
end
|
|
28
|
+
```
|
data/bin/tortard
ADDED
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
#! /usr/bin/env ruby
|
|
2
|
+
require 'eventmachine'
|
|
3
|
+
require 'tortard'
|
|
4
|
+
|
|
5
|
+
EM.run {
|
|
6
|
+
d = Tortard.load(ARGV.first || '~/.tortardrc')
|
|
7
|
+
d.start
|
|
8
|
+
|
|
9
|
+
%w[INT KILL].each {|sig|
|
|
10
|
+
trap sig do
|
|
11
|
+
puts 'torchatd stopping...'
|
|
12
|
+
|
|
13
|
+
d.stop
|
|
14
|
+
|
|
15
|
+
EM.stop_event_loop
|
|
16
|
+
end
|
|
17
|
+
}
|
|
18
|
+
}
|
data/lib/tortard.rb
ADDED
|
@@ -0,0 +1,78 @@
|
|
|
1
|
+
#--
|
|
2
|
+
# DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE
|
|
3
|
+
# Version 2, December 2004
|
|
4
|
+
#
|
|
5
|
+
# Copyleft meh. [http://meh.doesntexist.org | meh@paranoici.org]
|
|
6
|
+
#
|
|
7
|
+
# DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE
|
|
8
|
+
# TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
|
|
9
|
+
#
|
|
10
|
+
# 0. You just DO WHAT THE FUCK YOU WANT TO.
|
|
11
|
+
#++
|
|
12
|
+
|
|
13
|
+
require 'eventmachine'
|
|
14
|
+
|
|
15
|
+
require 'tortard/utils'
|
|
16
|
+
require 'tortard/address'
|
|
17
|
+
require 'tortard/map'
|
|
18
|
+
require 'tortard/bridge'
|
|
19
|
+
|
|
20
|
+
class Tortard
|
|
21
|
+
def self.load (path)
|
|
22
|
+
new.tap {|t|
|
|
23
|
+
t.load(path)
|
|
24
|
+
}
|
|
25
|
+
end
|
|
26
|
+
|
|
27
|
+
def initialize
|
|
28
|
+
@bridges = []
|
|
29
|
+
end
|
|
30
|
+
|
|
31
|
+
def load (path)
|
|
32
|
+
path = File.expand_path(path)
|
|
33
|
+
|
|
34
|
+
instance_eval File.read(path), path
|
|
35
|
+
end
|
|
36
|
+
|
|
37
|
+
def start
|
|
38
|
+
@bridges.each(&:start)
|
|
39
|
+
end
|
|
40
|
+
|
|
41
|
+
def stop
|
|
42
|
+
@bridges.each(&:stop)
|
|
43
|
+
end
|
|
44
|
+
|
|
45
|
+
def proxy (host, port = nil)
|
|
46
|
+
@proxy, tmp = port ? Address.new(host, port) : Address.parse(host)
|
|
47
|
+
|
|
48
|
+
yield
|
|
49
|
+
ensure
|
|
50
|
+
@proxy = tmp
|
|
51
|
+
end
|
|
52
|
+
|
|
53
|
+
def ssl (what)
|
|
54
|
+
@ssl, tmp = what, @ssl
|
|
55
|
+
|
|
56
|
+
yield
|
|
57
|
+
ensure
|
|
58
|
+
@ssl = tmp
|
|
59
|
+
end
|
|
60
|
+
|
|
61
|
+
def host (host)
|
|
62
|
+
@host, tmp = host, @host
|
|
63
|
+
|
|
64
|
+
yield
|
|
65
|
+
ensure
|
|
66
|
+
@host = tmp
|
|
67
|
+
end
|
|
68
|
+
|
|
69
|
+
def bridge (from, to)
|
|
70
|
+
if from.is_a?(Fixnum)
|
|
71
|
+
from = "#{@host}:#{from}"
|
|
72
|
+
end
|
|
73
|
+
|
|
74
|
+
@bridges << Bridge.new(@proxy || Address.parse('localhost:9050'), Address.parse(from), Address.parse(to), @ssl)
|
|
75
|
+
end
|
|
76
|
+
|
|
77
|
+
alias map bridge
|
|
78
|
+
end
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
#--
|
|
2
|
+
# DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE
|
|
3
|
+
# Version 2, December 2004
|
|
4
|
+
#
|
|
5
|
+
# Copyleft meh. [http://meh.doesntexist.org | meh@paranoici.org]
|
|
6
|
+
#
|
|
7
|
+
# DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE
|
|
8
|
+
# TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
|
|
9
|
+
#
|
|
10
|
+
# 0. You just DO WHAT THE FUCK YOU WANT TO.
|
|
11
|
+
#++
|
|
12
|
+
|
|
13
|
+
class Tortard
|
|
14
|
+
|
|
15
|
+
class Address
|
|
16
|
+
def self.parse (text)
|
|
17
|
+
new(*text.split(?:))
|
|
18
|
+
end
|
|
19
|
+
|
|
20
|
+
attr_reader :host, :port
|
|
21
|
+
|
|
22
|
+
def initialize (host, port)
|
|
23
|
+
@host = host
|
|
24
|
+
@port = port.to_i
|
|
25
|
+
end
|
|
26
|
+
|
|
27
|
+
def to_s
|
|
28
|
+
"#{host}:#{port}"
|
|
29
|
+
end
|
|
30
|
+
end
|
|
31
|
+
|
|
32
|
+
end
|
|
@@ -0,0 +1,49 @@
|
|
|
1
|
+
#--
|
|
2
|
+
# DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE
|
|
3
|
+
# Version 2, December 2004
|
|
4
|
+
#
|
|
5
|
+
# Copyleft meh. [http://meh.doesntexist.org | meh@paranoici.org]
|
|
6
|
+
#
|
|
7
|
+
# DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE
|
|
8
|
+
# TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
|
|
9
|
+
#
|
|
10
|
+
# 0. You just DO WHAT THE FUCK YOU WANT TO.
|
|
11
|
+
#++
|
|
12
|
+
|
|
13
|
+
require 'eventmachine'
|
|
14
|
+
require 'em-socksify'
|
|
15
|
+
|
|
16
|
+
require 'tortard/bridge/client'
|
|
17
|
+
require 'tortard/bridge/connection'
|
|
18
|
+
|
|
19
|
+
class Tortard
|
|
20
|
+
|
|
21
|
+
class Bridge
|
|
22
|
+
attr_reader :proxy, :from, :to, :ssl, :clients
|
|
23
|
+
|
|
24
|
+
def initialize (proxy, from, to, ssl = :none)
|
|
25
|
+
@proxy = proxy
|
|
26
|
+
@from = from
|
|
27
|
+
@to = to
|
|
28
|
+
@ssl = ssl
|
|
29
|
+
|
|
30
|
+
@clients = []
|
|
31
|
+
end
|
|
32
|
+
|
|
33
|
+
def start
|
|
34
|
+
@signature = EM.start_server to.host, to.port, Client do |c|
|
|
35
|
+
c.bridge = self
|
|
36
|
+
c.connect
|
|
37
|
+
|
|
38
|
+
@clients << c
|
|
39
|
+
end
|
|
40
|
+
end
|
|
41
|
+
|
|
42
|
+
def stop
|
|
43
|
+
@clients.each(&:disconnect)
|
|
44
|
+
|
|
45
|
+
EM.stop_server @signature
|
|
46
|
+
end
|
|
47
|
+
end
|
|
48
|
+
|
|
49
|
+
end
|
|
@@ -0,0 +1,66 @@
|
|
|
1
|
+
#--
|
|
2
|
+
# DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE
|
|
3
|
+
# Version 2, December 2004
|
|
4
|
+
#
|
|
5
|
+
# Copyleft meh. [http://meh.doesntexist.org | meh@paranoici.org]
|
|
6
|
+
#
|
|
7
|
+
# DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE
|
|
8
|
+
# TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
|
|
9
|
+
#
|
|
10
|
+
# 0. You just DO WHAT THE FUCK YOU WANT TO.
|
|
11
|
+
#++
|
|
12
|
+
|
|
13
|
+
class Tortard; class Bridge
|
|
14
|
+
|
|
15
|
+
class Client < EM::Connection
|
|
16
|
+
attr_accessor :bridge
|
|
17
|
+
|
|
18
|
+
def post_init
|
|
19
|
+
@buffer = []
|
|
20
|
+
end
|
|
21
|
+
|
|
22
|
+
def connect
|
|
23
|
+
if bridge.ssl == :both || bridge.ssl == :external
|
|
24
|
+
start_tls
|
|
25
|
+
end
|
|
26
|
+
|
|
27
|
+
EM.connect bridge.proxy.host, bridge.proxy.port, Connection do |c|
|
|
28
|
+
c.client = self
|
|
29
|
+
c.bridge = bridge
|
|
30
|
+
|
|
31
|
+
@connection = c
|
|
32
|
+
end
|
|
33
|
+
end
|
|
34
|
+
|
|
35
|
+
def receive_data (data)
|
|
36
|
+
if @buffer
|
|
37
|
+
@buffer << data
|
|
38
|
+
else
|
|
39
|
+
@connection.send_data data
|
|
40
|
+
end
|
|
41
|
+
end
|
|
42
|
+
|
|
43
|
+
def disconnect
|
|
44
|
+
close_connection_after_writing
|
|
45
|
+
end
|
|
46
|
+
|
|
47
|
+
def connected
|
|
48
|
+
Tortard.log "connected to #{bridge.from}"
|
|
49
|
+
|
|
50
|
+
buffer, @buffer = @buffer, nil
|
|
51
|
+
|
|
52
|
+
buffer.each {|data|
|
|
53
|
+
@connection.send_data data
|
|
54
|
+
}
|
|
55
|
+
end
|
|
56
|
+
|
|
57
|
+
def received (data)
|
|
58
|
+
send_data data
|
|
59
|
+
end
|
|
60
|
+
|
|
61
|
+
def unbind
|
|
62
|
+
@connection.close_connection_after_writing if @connection
|
|
63
|
+
end
|
|
64
|
+
end
|
|
65
|
+
|
|
66
|
+
end; end
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
#--; end
|
|
2
|
+
# DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE
|
|
3
|
+
# Version 2, December 2004
|
|
4
|
+
#
|
|
5
|
+
# Copyleft meh. [http://meh.doesntexist.org | meh@paranoici.org]
|
|
6
|
+
#
|
|
7
|
+
# DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE
|
|
8
|
+
# TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
|
|
9
|
+
#
|
|
10
|
+
# 0. You just DO WHAT THE FUCK YOU WANT TO.
|
|
11
|
+
#++
|
|
12
|
+
|
|
13
|
+
class Tortard; class Bridge
|
|
14
|
+
|
|
15
|
+
class Connection < EM::Connection
|
|
16
|
+
include EM::Socksify
|
|
17
|
+
|
|
18
|
+
attr_accessor :bridge, :client
|
|
19
|
+
|
|
20
|
+
def connection_completed
|
|
21
|
+
socksify(bridge.from.host, bridge.from.port).callback {
|
|
22
|
+
if bridge.ssl == :both || bridge.ssl == :internal
|
|
23
|
+
start_tls
|
|
24
|
+
end
|
|
25
|
+
|
|
26
|
+
@client.connected
|
|
27
|
+
}.errback {|e|
|
|
28
|
+
Tortard.log "failed to connect to #{bridge.from}"
|
|
29
|
+
}
|
|
30
|
+
end
|
|
31
|
+
|
|
32
|
+
def receive_data (data)
|
|
33
|
+
@client.received data
|
|
34
|
+
end
|
|
35
|
+
|
|
36
|
+
def send_data (data)
|
|
37
|
+
super
|
|
38
|
+
end
|
|
39
|
+
|
|
40
|
+
def unbind
|
|
41
|
+
@client.close_connection_after_writing if @client
|
|
42
|
+
end
|
|
43
|
+
end
|
|
44
|
+
|
|
45
|
+
end; end
|
data/lib/tortard/map.rb
ADDED
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
#--
|
|
2
|
+
# DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE
|
|
3
|
+
# Version 2, December 2004
|
|
4
|
+
#
|
|
5
|
+
# Copyleft meh. [http://meh.doesntexist.org | meh@paranoici.org]
|
|
6
|
+
#
|
|
7
|
+
# DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE
|
|
8
|
+
# TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
|
|
9
|
+
#
|
|
10
|
+
# 0. You just DO WHAT THE FUCK YOU WANT TO.
|
|
11
|
+
#++
|
|
12
|
+
|
|
13
|
+
require 'eventmachine'
|
|
14
|
+
require 'em-socksify'
|
|
15
|
+
|
|
16
|
+
require 'tortard/address'
|
|
17
|
+
|
|
18
|
+
class Tortard
|
|
19
|
+
|
|
20
|
+
class Map
|
|
21
|
+
attr_reader :socks, :from, :to
|
|
22
|
+
|
|
23
|
+
def initialize (socks, from, to)
|
|
24
|
+
@socks = socks
|
|
25
|
+
@from = from
|
|
26
|
+
@to = to
|
|
27
|
+
end
|
|
28
|
+
end
|
|
29
|
+
|
|
30
|
+
end
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
#--
|
|
2
|
+
# DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE
|
|
3
|
+
# Version 2, December 2004
|
|
4
|
+
#
|
|
5
|
+
# Copyleft meh. [http://meh.doesntexist.org | meh@paranoici.org]
|
|
6
|
+
#
|
|
7
|
+
# DO WHAT THE FUCK YOU WANT TO PUBLIC LICENSE
|
|
8
|
+
# TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
|
|
9
|
+
#
|
|
10
|
+
# 0. You just DO WHAT THE FUCK YOU WANT TO.
|
|
11
|
+
#++
|
|
12
|
+
|
|
13
|
+
class Tortard
|
|
14
|
+
def self.log (what)
|
|
15
|
+
puts "[#{Time.now}] #{what}"
|
|
16
|
+
end
|
|
17
|
+
end
|
data/tortard.gemspec
ADDED
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
Gem::Specification.new {|s|
|
|
2
|
+
s.name = 'tortard'
|
|
3
|
+
s.version = '0.0.1'
|
|
4
|
+
s.author = 'meh.'
|
|
5
|
+
s.email = 'meh@paranoici.org'
|
|
6
|
+
s.homepage = 'http://github.com/meh/tortard'
|
|
7
|
+
s.platform = Gem::Platform::RUBY
|
|
8
|
+
s.summary = 'Map SOCKS address:port to real:port.'
|
|
9
|
+
|
|
10
|
+
s.files = `git ls-files`.split("\n")
|
|
11
|
+
s.executables = `git ls-files -- bin/*`.split("\n").map { |f| File.basename(f) }
|
|
12
|
+
s.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
|
|
13
|
+
s.require_paths = ['lib']
|
|
14
|
+
|
|
15
|
+
s.add_dependency 'eventmachine', '>= 1.0.0.beta.4'
|
|
16
|
+
s.add_dependency 'em-socksify'
|
|
17
|
+
}
|
metadata
ADDED
|
@@ -0,0 +1,87 @@
|
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
|
2
|
+
name: tortard
|
|
3
|
+
version: !ruby/object:Gem::Version
|
|
4
|
+
version: 0.0.1
|
|
5
|
+
prerelease:
|
|
6
|
+
platform: ruby
|
|
7
|
+
authors:
|
|
8
|
+
- meh.
|
|
9
|
+
autorequire:
|
|
10
|
+
bindir: bin
|
|
11
|
+
cert_chain: []
|
|
12
|
+
date: 2012-05-18 00:00:00.000000000 Z
|
|
13
|
+
dependencies:
|
|
14
|
+
- !ruby/object:Gem::Dependency
|
|
15
|
+
name: eventmachine
|
|
16
|
+
requirement: !ruby/object:Gem::Requirement
|
|
17
|
+
none: false
|
|
18
|
+
requirements:
|
|
19
|
+
- - ! '>='
|
|
20
|
+
- !ruby/object:Gem::Version
|
|
21
|
+
version: 1.0.0.beta.4
|
|
22
|
+
type: :runtime
|
|
23
|
+
prerelease: false
|
|
24
|
+
version_requirements: !ruby/object:Gem::Requirement
|
|
25
|
+
none: false
|
|
26
|
+
requirements:
|
|
27
|
+
- - ! '>='
|
|
28
|
+
- !ruby/object:Gem::Version
|
|
29
|
+
version: 1.0.0.beta.4
|
|
30
|
+
- !ruby/object:Gem::Dependency
|
|
31
|
+
name: em-socksify
|
|
32
|
+
requirement: !ruby/object:Gem::Requirement
|
|
33
|
+
none: false
|
|
34
|
+
requirements:
|
|
35
|
+
- - ! '>='
|
|
36
|
+
- !ruby/object:Gem::Version
|
|
37
|
+
version: '0'
|
|
38
|
+
type: :runtime
|
|
39
|
+
prerelease: false
|
|
40
|
+
version_requirements: !ruby/object:Gem::Requirement
|
|
41
|
+
none: false
|
|
42
|
+
requirements:
|
|
43
|
+
- - ! '>='
|
|
44
|
+
- !ruby/object:Gem::Version
|
|
45
|
+
version: '0'
|
|
46
|
+
description:
|
|
47
|
+
email: meh@paranoici.org
|
|
48
|
+
executables:
|
|
49
|
+
- tortard
|
|
50
|
+
extensions: []
|
|
51
|
+
extra_rdoc_files: []
|
|
52
|
+
files:
|
|
53
|
+
- README.md
|
|
54
|
+
- bin/tortard
|
|
55
|
+
- lib/tortard.rb
|
|
56
|
+
- lib/tortard/address.rb
|
|
57
|
+
- lib/tortard/bridge.rb
|
|
58
|
+
- lib/tortard/bridge/client.rb
|
|
59
|
+
- lib/tortard/bridge/connection.rb
|
|
60
|
+
- lib/tortard/map.rb
|
|
61
|
+
- lib/tortard/utils.rb
|
|
62
|
+
- tortard.gemspec
|
|
63
|
+
homepage: http://github.com/meh/tortard
|
|
64
|
+
licenses: []
|
|
65
|
+
post_install_message:
|
|
66
|
+
rdoc_options: []
|
|
67
|
+
require_paths:
|
|
68
|
+
- lib
|
|
69
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
|
70
|
+
none: false
|
|
71
|
+
requirements:
|
|
72
|
+
- - ! '>='
|
|
73
|
+
- !ruby/object:Gem::Version
|
|
74
|
+
version: '0'
|
|
75
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
|
76
|
+
none: false
|
|
77
|
+
requirements:
|
|
78
|
+
- - ! '>='
|
|
79
|
+
- !ruby/object:Gem::Version
|
|
80
|
+
version: '0'
|
|
81
|
+
requirements: []
|
|
82
|
+
rubyforge_project:
|
|
83
|
+
rubygems_version: 1.8.24
|
|
84
|
+
signing_key:
|
|
85
|
+
specification_version: 3
|
|
86
|
+
summary: Map SOCKS address:port to real:port.
|
|
87
|
+
test_files: []
|