]>
git.ipfire.org Git - people/shoehn/ipfire.org.git/blob - www/pages/torrent/client/ServerPortHandler.py
1 # Written by John Hoffman
2 # see LICENSE.txt for license information
4 from cStringIO
import StringIO
5 #from RawServer import RawServer
12 from BT1
.Encrypter
import protocol_name
16 class SingleRawServer
:
17 def __init__(self
, info_hash
, multihandler
, doneflag
, protocol
):
18 self
.info_hash
= info_hash
19 self
.doneflag
= doneflag
20 self
.protocol
= protocol
21 self
.multihandler
= multihandler
22 self
.rawserver
= multihandler
.rawserver
30 self
.multihandler
.shutdown_torrent(self
.info_hash
)
36 self
.rawserver
.kill_tasks(self
.info_hash
)
38 self
.handler
.close_all()
40 def _external_connection_made(self
, c
, options
, already_read
):
42 c
.set_handler(self
.handler
)
43 self
.handler
.externally_handshaked_connection_made(
44 c
, options
, already_read
)
46 ### RawServer functions ###
48 def add_task(self
, func
, delay
=0, id = default_task_id
):
49 if id is default_task_id
:
52 self
.rawserver
.add_task(func
, delay
, id)
54 # def bind(self, port, bind = '', reuse = False):
55 # pass # not handled here
57 def start_connection(self
, dns
, handler
= None):
59 handler
= self
.handler
60 c
= self
.rawserver
.start_connection(dns
, handler
)
63 # def listen_forever(self, handler):
64 # pass # don't call with this
66 def start_listening(self
, handler
):
67 self
.handler
= handler
69 return self
.shutdown
# obviously, doesn't listen forever
71 def is_finished(self
):
74 def get_exception_flag(self
):
75 return self
.rawserver
.get_exception_flag()
78 class NewSocketHandler
: # hand a new socket off where it belongs
79 def __init__(self
, multihandler
, connection
):
80 self
.multihandler
= multihandler
81 self
.connection
= connection
82 connection
.set_handler(self
)
84 self
.buffer = StringIO()
86 self
.next_len
, self
.next_func
= 1, self
.read_header_len
87 self
.multihandler
.rawserver
.add_task(self
._auto
_close
, 15)
89 def _auto_close(self
):
95 self
.connection
.close()
100 # connection.write(chr(len(protocol_name)) + protocol_name +
101 # (chr(0) * 8) + self.encrypter.download_id + self.encrypter.my_id)
103 # copied from Encrypter and modified
105 def read_header_len(self
, s
):
107 return l
, self
.read_header
109 def read_header(self
, s
):
111 return 8, self
.read_reserved
113 def read_reserved(self
, s
):
115 return 20, self
.read_download_id
117 def read_download_id(self
, s
):
118 if self
.multihandler
.singlerawservers
.has_key(s
):
119 if self
.multihandler
.singlerawservers
[s
].protocol
== self
.protocol
:
123 def read_dead(self
, s
):
126 def data_came_in(self
, garbage
, s
):
130 i
= self
.next_len
- self
.buffer.tell()
134 self
.buffer.write(s
[:i
])
136 m
= self
.buffer.getvalue()
138 self
.buffer.truncate()
140 x
= self
.next_func(m
)
142 self
.next_len
, self
.next_func
= 1, self
.read_dead
147 if x
== True: # ready to process
148 self
.multihandler
.singlerawservers
[m
]._external
_connection
_made
(
149 self
.connection
, self
.options
, s
)
152 self
.next_len
, self
.next_func
= x
154 def connection_flushed(self
, ss
):
157 def connection_lost(self
, ss
):
161 def __init__(self
, rawserver
, doneflag
):
162 self
.rawserver
= rawserver
163 self
.masterdoneflag
= doneflag
164 self
.singlerawservers
= {}
165 self
.connections
= {}
168 def newRawServer(self
, info_hash
, doneflag
, protocol
=protocol_name
):
169 new
= SingleRawServer(info_hash
, self
, doneflag
, protocol
)
170 self
.singlerawservers
[info_hash
] = new
173 def shutdown_torrent(self
, info_hash
):
174 self
.singlerawservers
[info_hash
]._shutdown
()
175 del self
.singlerawservers
[info_hash
]
177 def listen_forever(self
):
178 self
.rawserver
.listen_forever(self
)
179 for srs
in self
.singlerawservers
.values():
184 ### RawServer handler functions ###
185 # be wary of name collisions
187 def external_connection_made(self
, ss
):
188 NewSocketHandler(self
, ss
)