def connection_flushed(self, connection): if self.connections[connection].done: if DEBUG2: log('HTTPHandler::connection_flushed: connection is done, call connection.shutdown') connection.shutdown(1) elif DEBUG2: log('HTTPHandler::connection_flushed: connection is not done')
def read_type(self, data): self.header = data.strip() words = data.split() if DEBUG2: log('HTTPConnection::read_type: data', data, 'words', words) if len(words) == 3: self.command, self.path, garbage = words self.pre1 = False elif len(words) == 2: self.command, self.path = words self.pre1 = True if self.command != 'GET': if DEBUG2: log('HTTPConnection::read_type: return none') return None else: if DEBUG2: log('HTTPConnection::read_type: return none') return None if self.command not in ('HEAD', 'GET'): if DEBUG2: log('HTTPConnection::read_type: return none') return None self.headers = {} if DEBUG2: log('HTTPConnection::read_type: command', self.command, 'path', self.path, 'next read_header()') return self.read_header
def got_piece(self, index): self.piecelock.acquire() try: if index in self.have: return start_new_file = False if DEBUG: log('vs::got_piece: index', index, 'thread', currentThread().getName()) if self.in_download_range(index): self.have.append(index) self.numhave += 1 self.completed = self.numhave / float(self.movie_numpieces) if not self.can_be_downloaded and self.completed >= self.min_download_percent: self.can_be_downloaded = True start_new_file = True if index in self.prebuf_high_priority_pieces: self.prebuf_high_priority_pieces.remove(index) if len(self.prebuf_missing_pieces): try: if index in self.prebuf_missing_pieces: self.prebuf_missing_pieces.remove(index) if len(self.prebuf_missing_pieces) == 0 and self.is_extra: self.prebuffering = False except: pass elif DEBUG: log('vs::got_piece: piece not in download range: index', index) return start_new_file finally: self.piecelock.release()
def guess_extension_from_mimetype(self, mimetype): if mimetype is None: mimetype = '' if mimetype == 'video/x-msvideo': ext = 'avi' elif mimetype == 'video/mp4': ext = 'mp4' elif mimetype == 'video/x-matroska': ext = 'mkv' elif mimetype == 'video/x-m4v': ext = 'm4v' elif mimetype == 'video/quicktime': ext = 'mov' elif mimetype == 'video/x-sgi-movie': ext = 'movie' elif mimetype == 'video/mpeg': ext = 'mpg' elif mimetype == 'application/ogg' or mimetype == 'video/ogg': ext = 'ogg' elif mimetype == 'video/x-flv': ext = 'flv' elif mimetype == 'video/webm': ext = 'webm' elif mimetype == 'video/x-ms-wmv': ext = 'wmv' else: if DEBUG: log(self.log_prefix + 'guess_extension_from_mimetype: unknown mimetype', mimetype) ext = 'mpg' if DEBUG: log(self.log_prefix + 'guess_extension_from_mimetype: mimetype', mimetype, 'ext', ext) return ext
def got_piece(self, index): self.piecelock.acquire() try: if index in self.have: return start_new_file = False if DEBUG: log('vs::got_piece: index', index, 'thread', currentThread().getName()) if self.in_download_range(index): self.have.append(index) self.numhave += 1 self.completed = self.numhave / float(self.movie_numpieces) if not self.can_be_downloaded and self.completed >= self.min_download_percent: self.can_be_downloaded = True start_new_file = True if index in self.prebuf_high_priority_pieces: self.prebuf_high_priority_pieces.remove(index) if len(self.prebuf_missing_pieces): try: if index in self.prebuf_missing_pieces: self.prebuf_missing_pieces.remove(index) if len(self.prebuf_missing_pieces ) == 0 and self.is_extra: self.prebuffering = False except: pass elif DEBUG: log('vs::got_piece: piece not in download range: index', index) return start_new_file finally: self.piecelock.release()
def shutdown(self): if DEBUG: log(self.log_prefix + 'shutdown: thread', currentThread().getName()) resumedata = None self.lock.acquire() try: if self.dow is not None: if self.repexer: repexer = self.unhook_repexer() repexer.repex_aborted(self.infohash, DLSTATUS_STOPPED) self.dldoneflag.set() self.dlrawserver.shutdown() resumedata = self.dow.shutdown() if DEBUG: log(self.log_prefix + 'shutdown: resumedata', resumedata) self.dow = None if self._hashcheckfunc is not None: if DEBUG: log(self.log_prefix + 'shutdown: reset _hashcheckfunc:', self._hashcheckfunc, 'thread', currentThread().getName()) self._hashcheckfunc = None if self._getstatsfunc is None or self._getstatsfunc == SPECIAL_VALUE: log(self.log_prefix + 'shutdown: shutdown on hashcheck: _getstatsfunc', self._getstatsfunc, 'thread', currentThread().getName()) self.lmhashcheckcompletecallback(self, success=False) elif DEBUG: log(self.log_prefix + 'shutdown: regular shutdown: _getstatsfunc', self._getstatsfunc, 'thread', currentThread().getName()) finally: self.lock.release() return resumedata
def __init__(self, timeout, ipv6_enable, readsize=100000, max_connects=1000): self.timeout = timeout self.ipv6_enable = ipv6_enable self.readsize = readsize self.poll = poll() self.single_sockets = {} self.dead_from_write = [] if max_connects <= 0: max_connects = 1000 if DEBUG: log('SocketHandler::__init__: max_connects', max_connects) self.max_connects = max_connects self.servers = {} self.btengine_said_reachable = False self.interrupt_socket = None self.udp_sockets = {} if globalConfig.get_mode() == 'stream' and globalConfig.get_value( 'private_source'): self.white_list = globalConfig.get_value('support_nodes') if DEBUG: log('SocketHandler::__init__: white_list', self.white_list) else: self.white_list = None
def give_up(self): self.lock.acquire() self.success = False self.finished = True if DEBUG_LOCK: log(self.log_prefix + 'give_up: self.success', self.success, 'self.finished', self.finished, 'thread', currentThread().name) self.lock.release()
def _set_piece_priority(self, new_priority): new_piece_priority = self._get_piece_priority_list(new_priority) pieces = range(self.numpieces) shuffle(pieces) new_blocked = [] new_unblocked = [] for piece in pieces: self.picker.set_priority(piece, new_piece_priority[piece]) o = self.piece_priority[piece] == -1 n = new_piece_priority[piece] == -1 if n and not o: new_blocked.append(piece) if o and not n: new_unblocked.append(piece) if DEBUG: log('FileSelector::_set_piece_priority: new_piece_priority', new_piece_priority, 'new_blocked', new_blocked, 'new_unblocked', new_unblocked) if new_blocked: self.cancelfunc(new_blocked) self.storagewrapper.reblock([i == -1 for i in new_piece_priority]) if new_unblocked: self.requestmorefunc(new_unblocked) return new_piece_priority
def set_priority(self, f, p): if DEBUG: log('FileSelector::set_priority: f', f, 'p', p) print_stack() new_priority = self.get_priorities() new_priority[f] = p self.set_priorities(new_priority)
def put(self, infohash, metadata, commit=True): if DEBUG: log('TsMetadataDBHandler::put: infohash', bin2str(infohash), 'metadata', metadata) data = {} if metadata.has_key('duration'): for idx, duration in metadata['duration'].iteritems(): data.setdefault(idx, {})['duration'] = duration if metadata.has_key('prebuf_pieces'): for idx, prebuf_pieces in metadata['prebuf_pieces'].iteritems(): data.setdefault(idx, {})['prebuf_pieces'] = prebuf_pieces if metadata.has_key('rpmp4mt'): for idx, replace_mp4_metatags in metadata['rpmp4mt'].iteritems(): data.setdefault( idx, {})['replace_mp4_metatags'] = replace_mp4_metatags if DEBUG: log('TsMetadataDBHandler::put: formatted data:', data) for idx, meta in data.iteritems(): idx = int(idx.replace('f', '')) self._db.insert_or_replace(self.table_name, commit=commit, infohash=bin2str(infohash), idx=idx, **meta)
def complete(self, piece): if DEBUG: log('pp::complete: piece', piece) self.pplock.acquire() try: if self.has[piece]: return False self.has[piece] = 1 self.numgot += 1 if DEBUG: print >> sys.stderr, 'PiecePicker::complete: piece:', piece, 'self.numgot:', self.numgot, 'self.numpieces', self.numpieces if self.numgot == self.numpieces: if DEBUG: print >> sys.stderr, 'PiecePicker::complete: self.done=True' self.done = True self.crosscount2 = self.crosscount else: numhaves = self.numhaves[piece] self.crosscount2[numhaves] -= 1 if numhaves + 1 == len(self.crosscount2): self.crosscount2.append(0) self.crosscount2[numhaves + 1] += 1 self._remove_from_interests(piece) return True finally: self.pplock.release()
def invalidate_piece(self, piece): if DEBUG: log('pp::invalidate_piece: piece', piece) self.pplock.acquire() try: if not self.has[piece]: return self.has[piece] = 0 self.numgot -= 1 p = self.priority[piece] level = self.numhaves[piece] + self.priority_step * p self.level_in_interests[piece] = level while len(self.interests) < level + 1: self.interests.append([]) l2 = self.interests[level] parray = self.pos_in_interests newp = randrange(len(l2) + 1) if newp == len(l2): parray[piece] = len(l2) l2.append(piece) else: old = l2[newp] parray[old] = len(l2) l2.append(old) l2[newp] = piece parray[piece] = newp finally: self.pplock.release()
def __init__(self, socket_handler, sock, handler, ip = None): self.socket_handler = socket_handler self.socket = sock self.handler = handler self.buffer = [] self.last_hit = clock() self.fileno = sock.fileno() self.connected = False self.skipped = 0 self.myip = None self.myport = -1 self.ip = None self.port = -1 try: myname = self.socket.getsockname() self.myip = myname[0] self.myport = myname[1] peername = self.socket.getpeername() self.ip = peername[0] self.port = peername[1] except: if ip is None: self.ip = 'unknown' else: self.ip = ip self.data_sent = 0 self.data_received = 0 if DEBUG: log('SingleSocket::__init__: myip', self.myip, 'myport', self.myport, 'ip', self.ip, 'port', self.port, 'handler', self.handler)
def bind(self, port, bind=[], reuse=False, ipv6_socket_style=1): port = int(port) addrinfos = [] self.servers = {} self.interfaces = [] if bind: if self.ipv6_enable: socktype = socket.AF_UNSPEC else: socktype = socket.AF_INET for addr in bind: if sys.version_info < (2, 2): addrinfos.append( (socket.AF_INET, None, None, None, (addr, port))) else: addrinfos.extend( socket.getaddrinfo(addr, port, socktype, socket.SOCK_STREAM)) else: if self.ipv6_enable: addrinfos.append( [socket.AF_INET6, None, None, None, ('', port)]) if not addrinfos or ipv6_socket_style != 0: addrinfos.append( [socket.AF_INET, None, None, None, ('', port)]) for addrinfo in addrinfos: try: server = socket.socket(addrinfo[0], socket.SOCK_STREAM) if reuse: server.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1) server.setblocking(0) if DEBUG: log('SocketHandler::bind: try to bind socket on', addrinfo[4]) server.bind(addrinfo[4]) self.servers[server.fileno()] = server bind_host, bind_port = server.getsockname() self.interfaces.append((bind_host, bind_port)) if DEBUG: log('SocketHandler::bind: socket bound: host', bind_host, 'port', bind_port) server.listen(64) self.poll.register(server, POLLIN) except socket.error as e: for server in self.servers.values(): try: server.close() except: pass if self.ipv6_enable and ipv6_socket_style == 0 and self.servers: raise socket.error( 'blocked port (may require ipv6_binds_v4 to be set)') raise socket.error(str(e)) if not self.servers: raise socket.error('unable to open server port') return self.interfaces[:]
def __init__(self, path, infohash, file_size, file_offset, piecelen, places = None, decrypt = True, offset_fix = None): self.path = path self.fp = open(self.path, 'rb') self.storage_secret = '8-90jm,2-=320fa&smnk/lsdgil,8as!8_' self.infohash = infohash file_begin = file_offset file_end = file_offset + file_size - 1 self.file_range = ((file_begin / piecelen, file_begin % piecelen), (file_end / piecelen, file_end % piecelen)) self.first_piecelen = piecelen - self.file_range[0][1] self.last_piecelen = self.file_range[1][1] + 1 self.first_piece = self.file_range[0][0] self.last_piece = self.file_range[1][0] self.numpieces = self.last_piece - self.first_piece + 1 self.piecelen = piecelen self.places = places self.decrypt = decrypt self.offset_fix = offset_fix self.file_offset = file_offset self.file_size = file_size self.cur_pos = 0 if self.decrypt: self.encrypt_pieces = {self.first_piece: 1, self.last_piece: 1} else: self.encrypt_pieces = {} if DEBUG: log('EncryptedStorageStream::__init__: path', path, 'decrypt', decrypt, 'size', file_size, 'offset', file_offset, 'piecelen', piecelen, 'first_piece', self.first_piece, 'last_piece', self.last_piece, 'places', places)
def __init__(self, socket_handler, sock, handler, ip=None): self.socket_handler = socket_handler self.socket = sock self.handler = handler self.buffer = [] self.last_hit = clock() self.fileno = sock.fileno() self.connected = False self.skipped = 0 self.myip = None self.myport = -1 self.ip = None self.port = -1 try: myname = self.socket.getsockname() self.myip = myname[0] self.myport = myname[1] peername = self.socket.getpeername() self.ip = peername[0] self.port = peername[1] except: if ip is None: self.ip = 'unknown' else: self.ip = ip self.data_sent = 0 self.data_received = 0 if DEBUG: log('SingleSocket::__init__: myip', self.myip, 'myport', self.myport, 'ip', self.ip, 'port', self.port, 'handler', self.handler)
def isfinished(self): self.lock.acquire() x = self.finished self.lock.release() if DEBUG_LOCK: log(self.log_prefix + 'isfinished: x', x, 'thread', currentThread().name) return x
def lost_have(self, piece): if DEBUG: log('pp::lost_have: piece', piece) self.pplock.acquire() try: self.totalcount -= 1 if self.totalcount < 0: self.totalcount = 0 numint = self.numhaves[piece] if numint <= 0: return self.numhaves[piece] -= 1 self.crosscount[numint] -= 1 self.crosscount[numint - 1] += 1 if not self.done: numintplus = numint + self.has[piece] self.crosscount2[numintplus] -= 1 if numintplus > 0: self.crosscount2[numintplus - 1] += 1 numint = self.level_in_interests[piece] self.level_in_interests[piece] -= 1 if self.superseed: numint = self.level_in_interests[piece] self.level_in_interests[piece] -= 1 elif self.has[piece] or self.priority[piece] == -1: return self._shift_over(piece, self.interests[numint], self.interests[numint - 1]) finally: self.pplock.release()
def set_prebuf_pieces(self, prebuf_extra_pieces): self.piecelock.acquire() try: if DEBUG: log('vs::set_prebuf_pieces: prebuf_extra_pieces', prebuf_extra_pieces) prebuf_needed_pieces = [] prebuf_pieces = min(self.movie_numpieces, 2 * self.get_high_range_length()) prebuf_needed_pieces.extend( self.generate_range( (self.first_piece, self.first_piece + prebuf_pieces))) if len(prebuf_extra_pieces) == 1 and prebuf_extra_pieces[0] == 0: prebuf_extra_pieces = [] prebuf_needed_pieces.extend(prebuf_extra_pieces) prebuf_needed_pieces = list(set(prebuf_needed_pieces)) prebuf_needed_pieces.sort() prebuf_missing_pieces = filter(lambda i: i not in self.have, prebuf_needed_pieces) if DEBUG: log('vs::set_prebuf_pieces: prebuf_pieces', prebuf_pieces, 'prebuf_needed_pieces', prebuf_needed_pieces, 'prebuf_missing_pieces', prebuf_missing_pieces) self.prebuf_pieces = prebuf_pieces self.prebuf_needed_pieces = prebuf_needed_pieces self.prebuf_missing_pieces = prebuf_missing_pieces except: if DEBUG: print_exc() finally: self.piecelock.release()
def invalidate_piece(self, piece): if DEBUG: log('pp::invalidate_piece: piece', piece) self.pplock.acquire() try: if not self.has[piece]: return self.has[piece] = 0 self.numgot -= 1 p = self.priority[piece] level = self.numhaves[piece] + self.priority_step * p self.level_in_interests[piece] = level while len(self.interests) < level + 1: self.interests.append([]) l2 = self.interests[level] parray = self.pos_in_interests newp = randrange(len(l2) + 1) if newp == len(l2): parray[piece] = len(l2) l2.append(piece) else: old = l2[newp] parray[old] = len(l2) l2.append(old) l2[newp] = piece parray[piece] = newp finally: self.pplock.release()
def got_invalidate(self, index): if DEBUG: log('downloader::got_invalidate: index', index) if not self.have[index]: return self.have[index] = False self.downloader.picker.lost_have(index)
def complete(self, piece): if DEBUG: log('pp::complete: piece', piece) self.pplock.acquire() try: if self.has[piece]: return False self.has[piece] = 1 self.numgot += 1 if DEBUG: print >> sys.stderr, 'PiecePicker::complete: piece:', piece, 'self.numgot:', self.numgot, 'self.numpieces', self.numpieces if self.numgot == self.numpieces: if DEBUG: print >> sys.stderr, 'PiecePicker::complete: self.done=True' self.done = True self.crosscount2 = self.crosscount else: numhaves = self.numhaves[piece] self.crosscount2[numhaves] -= 1 if numhaves + 1 == len(self.crosscount2): self.crosscount2.append(0) self.crosscount2[numhaves + 1] += 1 self._remove_from_interests(piece) return True finally: self.pplock.release()
def __init__(self, doneflag, timeout_check_interval, timeout, noisy = True, ipv6_enable = True, failfunc = lambda x: None, errorfunc = None, sockethandler = None, excflag = Event(), max_socket_connects = 1000): self.timeout_check_interval = timeout_check_interval self.timeout = timeout self.servers = {} self.single_sockets = {} self.dead_from_write = [] self.doneflag = doneflag self.noisy = noisy self.failfunc = failfunc self.errorfunc = errorfunc self.exccount = 0 self.funcs = [] self.externally_added = [] self.finished = Event() self.tasks_to_kill = [] self.excflag = excflag self.lock = RLock() if DEBUG2: log('rawserver::__init__: timeout_check_interval', timeout_check_interval, 'timeout', timeout, 'ipv6_enable', ipv6_enable) if sockethandler is None: if DEBUG2: log('rawserver::__init__: create SocketHandler: max_socket_connects', max_socket_connects) sockethandler = SocketHandler(timeout, ipv6_enable, READSIZE, max_socket_connects) self.sockethandler = sockethandler self.thread_ident = None self.interrupt_socket = sockethandler.get_interrupt_socket() self.add_task(self.scan_for_timeouts, timeout_check_interval)
def _next(self, haves, wantfunc, complete_first, helper_con, willrequest = True, connection = None, shuffle = True): cutoff = self.numgot < self.rarest_first_cutoff complete_first = (complete_first or cutoff) and not haves.complete() best = None bestnum = 1073741824 for i in self.started: if haves[i] and wantfunc(i) and (self.helper is None or helper_con or not self.helper.is_ignored(i)): if self.level_in_interests[i] < bestnum: best = i bestnum = self.level_in_interests[i] if best is not None: if complete_first or cutoff and len(self.interests) > self.cutoff: return best if DEBUG: log('pp:_next: haves.complete()', haves.complete()) if haves.complete(): r = [(0, min(bestnum, len(self.interests)))] elif cutoff and len(self.interests) > self.cutoff: r = [(self.cutoff, min(bestnum, len(self.interests))), (0, self.cutoff)] else: r = [(0, min(bestnum, len(self.interests)))] if DEBUG: log('pp:_next: r', r, 'interests', self.interests) for lo, hi in r: for i in xrange(lo, hi): for j in self.interests[i]: if haves[j] and wantfunc(j) and (self.helper is None or helper_con or not self.helper.is_ignored(j)): return j if best is not None: return best
def lost_have(self, piece): if DEBUG: log('pp::lost_have: piece', piece) self.pplock.acquire() try: self.totalcount -= 1 if self.totalcount < 0: self.totalcount = 0 numint = self.numhaves[piece] if numint <= 0: return self.numhaves[piece] -= 1 self.crosscount[numint] -= 1 self.crosscount[numint - 1] += 1 if not self.done: numintplus = numint + self.has[piece] self.crosscount2[numintplus] -= 1 if numintplus > 0: self.crosscount2[numintplus - 1] += 1 numint = self.level_in_interests[piece] self.level_in_interests[piece] -= 1 if self.superseed: numint = self.level_in_interests[piece] self.level_in_interests[piece] -= 1 elif self.has[piece] or self.priority[piece] == -1: return self._shift_over(piece, self.interests[numint], self.interests[numint - 1]) finally: self.pplock.release()
def next_have(self, connection, looser_upload): if DEBUG: log('pp::next_have: ---') if self.seed_time is None: self.seed_time = clock() return if clock() < self.seed_time + 10: return if not connection.upload.super_seeding: return if connection in self.seed_connections: if looser_upload: num = 1 else: num = 2 if self.seed_got_haves[self.seed_connections[connection]] < num: return if not connection.upload.was_ever_interested: connection.upload.skipped_count += 1 if connection.upload.skipped_count >= 3: return -1 for tier in self.interests: for piece in tier: if not connection.download.have[piece]: seedint = self.level_in_interests[piece] self.level_in_interests[piece] += 1 if seedint == len(self.interests) - 1: self.interests.append([]) self._shift_over(piece, self.interests[seedint], self.interests[seedint + 1]) self.seed_got_haves[piece] = 0 self.seed_connections[connection] = piece connection.upload.seed_have_list.append(piece) return piece return -1
def data_came_in(self, data): if DEBUG2: log('HTTPConnection::data_came_in: data_len', len(data), 'data', data) if self.donereading or self.next_func is None: if DEBUG2: log('HTTPConnection::data_came_in: skip and return True: donereading', self.donereading, 'or next_func', self.next_func) return True self.buf += data if DEBUG2: log('HTTPConnection::data_came_in: buf_len', len(self.buf)) while 1: try: i = self.buf.index('\n') except ValueError: return True val = self.buf[:i] self.buf = self.buf[i + 1:] self.next_func = self.next_func(val) if self.donereading: if DEBUG2: log('HTTPConnection::data_came_in: donereading, return True') return True if self.next_func is None or self.closed: if DEBUG2: log('HTTPConnection::data_came_in: break and return False: next_func', self.next_func, 'or closed', self.closed) return False
def got_have(self, piece, connection = None): if DEBUG: log('pp::got_have: piece', piece) self.pplock.acquire() try: self.totalcount += 1 numint = self.numhaves[piece] self.numhaves[piece] += 1 self.crosscount[numint] -= 1 if numint + 1 == len(self.crosscount): self.crosscount.append(0) self.crosscount[numint + 1] += 1 if not self.done: numintplus = numint + self.has[piece] self.crosscount2[numintplus] -= 1 if numintplus + 1 == len(self.crosscount2): self.crosscount2.append(0) self.crosscount2[numintplus + 1] += 1 numint = self.level_in_interests[piece] self.level_in_interests[piece] += 1 if self.superseed: self.seed_got_haves[piece] += 1 numint = self.level_in_interests[piece] self.level_in_interests[piece] += 1 else: if self.has[piece]: return True if self.priority[piece] == -1: return False if numint == len(self.interests) - 1: self.interests.append([]) self._shift_over(piece, self.interests[numint], self.interests[numint + 1]) return False finally: self.pplock.release()
def delete_temp_file(self, start): if self.temp_files.has_key(start): path = self.temp_files[start] if DEBUG: log(self.log_prefix + 'delete_temp_file: start', start, 'path', path) self._close(path) os.remove(path)
def close(self): if DEBUG2: log('NewSocketHandler::close: complete', self.complete, 'ip', self.connection.get_ip(), 'port', self.connection.get_port()) if not self.closed: self.connection.close() self.closed = True
def acquire_inputstream(self, urlpath): global DEBUG if urlpath is None: return streaminfo = None for mapper in self.mappers: streaminfo = mapper.get(urlpath) if streaminfo is not None and (streaminfo['statuscode'] == 200 or streaminfo['statuscode'] == 301): return streaminfo self.lock.acquire() if DEBUGLOCK: log('VideoServer::acquire_inputstream: lock done', urlpath, currentThread().getName()) try: streaminfo = self.urlpath2streaminfo.get(urlpath, None) if DEBUG: log('videoserver::acquire_inputstream: got streaminfo: urlpath', urlpath, 'streaminfo', streaminfo) finally: if DEBUGLOCK: log('VideoServer::acquire_inputstream: unlock', urlpath, currentThread().getName()) self.lock.release() if streaminfo is not None and 'lock' in streaminfo: if DEBUGLOCK: log('VideoServer::acquire_inputstream: lock stream: urlpath', urlpath, 'streaminfo', streaminfo, 'thread', currentThread().getName()) streaminfo['lock'].acquire() if DEBUGLOCK: log('VideoServer::acquire_inputstream: lock stream done: urlpath', urlpath, 'thread', currentThread().getName()) return streaminfo
def newRawServer(self, info_hash, doneflag, protocol=protocol_name): new = SingleRawServer(info_hash, self, doneflag, protocol) self.singlerawservers[info_hash] = new if DEBUG: log('multihandler::newRawServer: infohash', info_hash, 'protocol', protocol, 'count_single_servers', len(self.singlerawservers)) return new
def init_check_network_connection(self): t = Thread(target=self.check_network_connection, args=[False, 5, True]) t.name = 'RerequestCheckNetwork' + t.name t.daemon = True if DEBUG_LOCK or DEBUG_ANNOUNCE: log(self.log_prefix + 'init_check_network_connection: start check_network_connection(): thread', t.name) t.start()
def external_connection_made(self, ss): if DEBUG2: log( 'multihandler::external_connection_made: create NewSocketHandler: ss', ss, 'count_single_servers', len(self.singlerawservers), 'count_connections', len(self.connections)) NewSocketHandler(self, ss)
def unwait(self, code): if code == self.code and self.pause.locked(): if DEBUG_LOCK: log(self.log_prefix + 'unwait: release pause: code', code, 'self.code', self.code, 'thread', currentThread().name) self.pause.release() elif DEBUG_LOCK: log(self.log_prefix + 'unwait: do not release pause: code', code, 'self.code', self.code, 'thread', currentThread().name)
def start_listening(self, handler): if DEBUG: log('SingleRawServer::start_listening: handler', handler, 'running', self.running) self.handler = handler self.running = True return self.shutdown
def start_connection(self, dns, handler = None): if DEBUG2: log('SingleRawServer::start_connection: dns', dns, 'handler', handler, 'self.handler', self.handler) if not handler: handler = self.handler c = self.rawserver.start_connection(dns, handler) return c
def del_inputstream(self, urlpath): if DEBUGLOCK: log('VideoServer::del_inputstream: enter', urlpath) streaminfo = self.acquire_inputstream(urlpath) self.lock.acquire() if DEBUGLOCK: log('VideoServer::del_inputstream: lock', urlpath, currentThread().getName()) try: del self.urlpath2streaminfo[urlpath] except KeyError: if DEBUGLOCK: log('videoserver::del_inputstream: path not found: urlpath', urlpath) finally: if DEBUGLOCK: log('VideoServer::del_inputstream: unlock', urlpath, currentThread().getName()) self.lock.release() if streaminfo is not None and 'lock' in streaminfo: if DEBUGLOCK: log('VideoServer::del_inputstream: stream: unlock', urlpath, currentThread().getName()) streaminfo['lock'].release()
def set_bitrate(self, bitrate, fake_bitrate=False): self.bitrate_set = not fake_bitrate self.bitrate = bitrate self.piece_per_sec = float(bitrate) / self.piecelen if DEBUG: log('vs::set_bitrate: bitrate', bitrate, 'fake', fake_bitrate, 'piece_per_sec', self.piece_per_sec)
def endElement(self, name): n = name.lower() if n == 'servicetype': if self.current_service is None: if DEBUG: log( 'upnp::DescriptionContentHandler::endElement: not in <service>: name', name) return self.current_service['type'] = self.content elif n == 'controlurl': if self.current_service is None: if DEBUG: log( 'upnp::DescriptionContentHandler::endElement: not in <service>: name', name) return self.current_service['url'] = self.content elif n == 'service': s = { 'type': self.current_service['type'], 'url': self.current_service['url'] } self.services.append(s) self.current_service = None
def set_max_conns(self, nconns, callback): if self.dow is not None: if DEBUG: log(self.log_prefix + 'set_max_conns', `(self.dow.response['info']['name'])`) self.dow.setMaxConns(nconns, networkcalling=True) if callback is not None: callback(nconns)
def send_torrent(self, torrent_data, developer_id = None, affiliate_id = None, zone_id = None, protected = False, infohash = None): params = {} if developer_id is not None: params['d'] = str(developer_id) if affiliate_id is not None: params['a'] = str(affiliate_id) if zone_id is not None: params['z'] = str(zone_id) if protected: params['protected'] = '1' if infohash is not None: params['infohash'] = binascii.hexlify(infohash) response = self.send_request('puttorrent', params, data=torrent_data, content_type='application/octet-stream', use_random=True) if response is None: if DEBUG: log('tsservice::send_torrent: request failed') return try: player_id = domutils.get_tag_value(response, 'id') except Exception as e: if DEBUG: log('tsservice::send_torrent: failed to parse response: ' + str(e)) return return player_id
def live_seek(self, pos): if DEBUG: log(self.log_prefix + 'live_seek: pos', pos) if self.dow is None: log(self.log_prefix + 'live_seek: dow is none') return self.dow.live_seek(pos)
def check_response(self, response, request_random = None): if len(response) == 0: raise BadResponseException, 'Empty response' doc = parseString(response) root = doc.documentElement if root.tagName != 'response': raise BadResponseException, 'Bad response tagname: ' + doc.tagName if not root.hasAttribute('sig'): raise BadResponseException, 'Missing signature' if request_random is not None: if not root.hasAttribute('r'): raise BadResponseException, 'Missing random' try: response_random = int(root.getAttribute('r')) except ValueError: raise BadResponseException, 'Cannot parse random' if response_random != request_random: if DEBUG: log('tsservice::check_response: bad random: response_random', response_random, 'request_random', request_random) raise BadResponseException, 'Bad random' response_sig = root.getAttribute('sig') payload = response.replace(' sig="' + response_sig + '"', '', 1) if DEBUG: log('tsservice::check_response: response', response) log('tsservice::check_response: response_sig', response_sig) log('tsservice::check_response: payload', payload) check_sig = hashlib.sha1(payload + self.RESPONSE_SECRET).hexdigest() if check_sig != response_sig: if DEBUG: log('tsservice::check_response: bad sig: response_sig', response_sig, 'check_sig', check_sig) raise BadResponseException, 'Bad signature' return doc
def try_ban(self, ip): log('downloader::try_ban: ip', ip) if self._check_kicks_ok(): self.banfunc(ip) self.banned[ip] = self.perip[ip].peerid if self.kicked.has_key(ip): del self.kicked[ip]
def __init__(self, i2iport, connhandler, timeout = 300.0, port_file = None): Thread.__init__(self) self.setDaemon(True) self.setName('Instance2Instance' + self.getName()) self.i2iport = i2iport self.port_file = port_file self.connhandler = connhandler self.i2idoneflag = Event() self.rawserver = RawServer(self.i2idoneflag, timeout / 5.0, timeout, ipv6_enable=False, failfunc=self.rawserver_fatalerrorfunc, errorfunc=self.rawserver_nonfatalerrorfunc) self.rawserver.add_task(self.rawserver_keepalive, 1) if globalConfig.get_value('allow-non-local-client-connection'): interfaces = self.rawserver.bind(self.i2iport, reuse=True) else: interfaces = self.rawserver.bind(self.i2iport, bind=['127.0.0.1'], reuse=True) if DEBUG: log('i2is::init: bound on interfaces', interfaces) if i2iport == 0 and len(interfaces): host, port = interfaces[0] self.i2iport = port if port_file is not None: f = None try: f = open(port_file, 'w') f.write(str(port)) except: if DEBUG: log('i2is::init: cannot save port to file', port_file) raise Exception, 'Cannot save port' finally: if f: f.close()
def write_temp_file(self, start, pos, data): if self.closed: if DEBUG: log( self.log_prefix + 'write_temp_file: storage is closed: start', start, 'pos', pos) return False if not self.temp_files.has_key(start): temp_filename = self.fileinfo['filename'] + '.' + str( start) + '.tmp' path = os.path.join(self.temp_dir, temp_filename) if DEBUG: log( self.log_prefix + 'write_temp_file: create temp file: start', start, 'pos', pos, 'path', path) f = open(path, 'wb+') f.flush() f.close() self.temp_files[start] = path self.mtimes[path] = os.path.getmtime(path) self.tops[path] = os.path.getsize(path) path = self.temp_files[start] h = self.get_file_handle(path, True) h.seek(pos) h.write(data) return True
def stop(self): if DEBUG: log('tns::stop: stopped', self.stopped) if not self.stopped: self.send_event('STOP') self.tqueue.add_task('quit') self.download_stopped = True
def set_url_list(self, url_list): if DEBUG: log('tstats::set_url_list:', url_list) if url_list is None: self.url_list = None else: self.url_list = url_list
def __init__(self, getfunc, minflush): self.connections = {} self.getfunc = getfunc self.minflush = minflush self.lastflush = clock() if DEBUG: log('HTTPHandler::__init__: ---')
def __init__(self, main_url, download_url, dlhash, config, multihandler, fileinfo, resumedata, vodeventcallback, set_error_func, finished_func, failed_func): self.main_url = main_url self.download_url = download_url self.dlhash = dlhash self.config = config self.dlmode = config['mode'] self.fileinfo = fileinfo self.vodeventcallback = vodeventcallback self.set_error_func = set_error_func self.finished_func = finished_func self.failed_func = failed_func self.download_id = binascii.hexlify(self.dlhash) + '-' + str(long(time.time())) + '-' + str(random.randint(0, 100000)) self.dldoneflag = Event() self.rawserver = multihandler.newRawServer(dlhash, self.dldoneflag) if download_url is not None: url = download_url else: url = main_url self.downloader = Downloader(url, dlhash, self.rawserver, self.failed) self.voddownload = None self.storage = None self.log_prefix = 'dd::' + binascii.hexlify(self.dlhash) + ':' predownload = self.config.get('predownload', False) if DEBUG: log(self.log_prefix + '__init__: predownload', predownload) if resumedata is None and predownload: self.downloader.predownload(self.init_predownloaded) else: callback = lambda content_length, mimetype: self.init(resumedata, content_length, mimetype) self.downloader.init(callback)
def close(self, closeall=False): if DEBUG: log('Encoder.Connection::close: ip', self.get_ip(), 'port', self.get_port()) if not self.closed: self.connection.close() self.sever(closeall=closeall)