diff --git a/shadowsocks/obfsplugin/auth.py b/shadowsocks/obfsplugin/auth.py index 2197a5b..012236f 100644 --- a/shadowsocks/obfsplugin/auth.py +++ b/shadowsocks/obfsplugin/auth.py @@ -277,7 +277,7 @@ class auth_simple(verify_base): def server_post_decrypt(self, buf): if self.raw_trans: - return buf + return (buf, False) self.recv_buf += buf out_buf = b'' while len(self.recv_buf) > 2: @@ -287,7 +287,7 @@ class auth_simple(verify_base): self.recv_buf = b'' if self.decrypt_packet_num == 0: logging.info('auth_simple: over size') - return b'E' + return (b'E', False) else: raise Exception('server_post_decrype data error') if length > len(self.recv_buf): @@ -298,7 +298,7 @@ class auth_simple(verify_base): self.raw_trans = True self.recv_buf = b'' if self.decrypt_packet_num == 0: - return b'E' + return (b'E', False) else: raise Exception('server_post_decrype data uncorrect CRC32') @@ -309,7 +309,7 @@ class auth_simple(verify_base): self.raw_trans = True self.recv_buf = b'' logging.info('auth_simple: too short') - return b'E' + return (b'E', False) utc_time = struct.unpack('H', self.recv_buf[4:6])[0] if length > len(self.recv_buf): - return b'' + return (b'', False) sha1data = hmac.new(self.server_info.recv_iv + self.server_info.key, self.recv_buf[:length - 10], hashlib.sha1).digest()[:10] if sha1data != self.recv_buf[length - 10:length]: logging.error('auth_sha1 data uncorrect auth HMAC-SHA1') - return b'E' + return (b'E', False) pos = common.ord(self.recv_buf[6]) + 6 out_buf = self.recv_buf[pos:length - 10] if len(out_buf) < 12: self.raw_trans = True self.recv_buf = b'' logging.info('auth_sha1: too short') - return b'E' + return (b'E', False) utc_time = struct.unpack(' len(self.recv_buf): @@ -514,7 +514,7 @@ class auth_sha1(verify_base): self.raw_trans = True self.recv_buf = b'' if self.decrypt_packet_num == 0: - return b'E' + return (b'E', False) else: raise Exception('server_post_decrype data uncorrect checksum') @@ -525,7 +525,7 @@ class auth_sha1(verify_base): if out_buf: self.server_info.data.update(self.client_id, self.connection_id) self.decrypt_packet_num += 1 - return out_buf + return (out_buf, False) class obfs_auth_v2_data(object): def __init__(self): @@ -686,26 +686,26 @@ class auth_sha1_v2(verify_base): def server_post_decrypt(self, buf): if self.raw_trans: - return buf + return (buf, False) self.recv_buf += buf out_buf = b'' if not self.has_recv_header: if len(self.recv_buf) < 4: - return b'' + return (b'', False) crc = struct.pack('H', self.recv_buf[4:6])[0] if length > len(self.recv_buf): - return b'' + return (b'', False) sha1data = hmac.new(self.server_info.recv_iv + self.server_info.key, self.recv_buf[:length - 10], hashlib.sha1).digest()[:10] if sha1data != self.recv_buf[length - 10:length]: logging.error('auth_sha1_v2 data uncorrect auth HMAC-SHA1') - return b'E' + return (b'E', False) pos = common.ord(self.recv_buf[6]) if pos < 255: pos += 6 @@ -716,7 +716,7 @@ class auth_sha1_v2(verify_base): self.raw_trans = True self.recv_buf = b'' logging.info('auth_sha1_v2: too short') - return b'E' + return (b'E', False) client_id = struct.unpack(' 2: length = struct.unpack('>H', self.recv_buf[:2])[0] if length >= 8192 or length < 7: @@ -739,7 +740,7 @@ class auth_sha1_v2(verify_base): self.recv_buf = b'' if self.decrypt_packet_num == 0: logging.info('auth_sha1_v2: over size') - return b'E' + return (b'E', False) else: raise Exception('server_post_decrype data error') if length > len(self.recv_buf): @@ -750,7 +751,7 @@ class auth_sha1_v2(verify_base): self.raw_trans = True self.recv_buf = b'' if self.decrypt_packet_num == 0: - return b'E' + return (b'E', False) else: raise Exception('server_post_decrype data uncorrect checksum') @@ -761,9 +762,11 @@ class auth_sha1_v2(verify_base): pos = struct.unpack('>H', self.recv_buf[3:5])[0] + 2 out_buf += self.recv_buf[pos:length - 4] self.recv_buf = self.recv_buf[length:] + if pos == length - 4: + sendback = True if out_buf: self.server_info.data.update(self.client_id, self.connection_id) self.decrypt_packet_num += 1 - return out_buf + return (out_buf, sendback) diff --git a/shadowsocks/obfsplugin/plain.py b/shadowsocks/obfsplugin/plain.py index 8bb0000..f8a733a 100644 --- a/shadowsocks/obfsplugin/plain.py +++ b/shadowsocks/obfsplugin/plain.py @@ -67,7 +67,7 @@ class plain(object): return (buf, True, False) def server_post_decrypt(self, buf): - return buf + return (buf, False) def client_udp_pre_encrypt(self, buf): return buf diff --git a/shadowsocks/obfsplugin/verify.py b/shadowsocks/obfsplugin/verify.py index 639ba5c..8f6b8c6 100644 --- a/shadowsocks/obfsplugin/verify.py +++ b/shadowsocks/obfsplugin/verify.py @@ -151,7 +151,7 @@ class verify_simple(verify_base): def server_post_decrypt(self, buf): if self.raw_trans: - return buf + return (buf, False) self.recv_buf += buf out_buf = b'' while len(self.recv_buf) > 2: @@ -160,7 +160,7 @@ class verify_simple(verify_base): self.raw_trans = True self.recv_buf = b'' if self.decrypt_packet_num == 0: - return b'E' + return (b'E', False) else: raise Exception('server_post_decrype data error') if length > len(self.recv_buf): @@ -170,7 +170,7 @@ class verify_simple(verify_base): self.raw_trans = True self.recv_buf = b'' if self.decrypt_packet_num == 0: - return b'E' + return (b'E', False) else: raise Exception('server_post_decrype data uncorrect CRC32') @@ -180,7 +180,7 @@ class verify_simple(verify_base): if out_buf: self.decrypt_packet_num += 1 - return out_buf + return (out_buf, False) class verify_deflate(verify_base): def __init__(self, method): @@ -236,7 +236,7 @@ class verify_deflate(verify_base): def server_post_decrypt(self, buf): if self.raw_trans: - return buf + return (buf, False) self.recv_buf += buf out_buf = b'' while len(self.recv_buf) > 2: @@ -256,7 +256,7 @@ class verify_deflate(verify_base): if out_buf: self.decrypt_packet_num += 1 - return out_buf + return (out_buf, False) class verify_sha1(verify_base): def __init__(self, method): @@ -303,26 +303,26 @@ class verify_sha1(verify_base): def server_post_decrypt(self, buf): if self.raw_trans: - return buf + return (buf, False) self.recv_buf += buf out_buf = b'' if not self.has_recv_header: if len(self.recv_buf) < 2: - return b'' + return (b'', False) if (ord(self.recv_buf[0]) & 0x10) != 0x10: if self.method == 'verify_sha1': logging.error('Not One-time authentication header') - return b'E' + return (b'E', False) else: self.raw_trans = True - return self.recv_buf + return (self.recv_buf, False) head_size = self.get_head_size(self.recv_buf, 30) if len(self.recv_buf) < head_size + 10: - return b'' + return (b'', False) sha1data = hmac.new(self.server_info.recv_iv + self.server_info.key, self.recv_buf[:head_size], hashlib.sha1).digest()[:10] if sha1data != self.recv_buf[head_size:head_size + 10]: logging.error('server_post_decrype data uncorrect auth HMAC-SHA1') - return b'E' + return (b'E', False) out_buf = to_bytes(chr(ord(self.recv_buf[0]) & 0xEF)) + self.recv_buf[1:head_size] self.recv_buf = self.recv_buf[head_size + 10:] self.has_recv_header = True @@ -340,7 +340,7 @@ class verify_sha1(verify_base): out_buf += data self.recv_buf = self.recv_buf[length:] - return out_buf + return (out_buf, False) def client_udp_pre_encrypt(self, buf): ret = self.pack_auth_data(buf) diff --git a/shadowsocks/tcprelay.py b/shadowsocks/tcprelay.py index 1349f62..121f056 100644 --- a/shadowsocks/tcprelay.py +++ b/shadowsocks/tcprelay.py @@ -364,7 +364,7 @@ class TCPRelayHandler(object): return (host_post, 80) def _handel_protocol_error(self, client_address, ogn_data): - logging.warn("Protocol ERROR, TCP ogn data %s from %s:%d" % (binascii.hexlify(ogn_data), client_address[0], client_address[1])) + logging.warn("Protocol ERROR, TCP ogn data %s from %s:%d via port %d" % (binascii.hexlify(ogn_data), client_address[0], client_address[1], self._server._listen_port)) self._encrypt_correct = False #create redirect or disconnect by hash code host, port = self._get_redirect_host(client_address, ogn_data) @@ -518,12 +518,17 @@ class TCPRelayHandler(object): if not self._remote_udp: if self._forbidden_iplist: if common.to_str(sa[0]) in self._forbidden_iplist: + if self._remote_address: + raise Exception('IP %s is in forbidden list, when connect to %s:%d via port %d' % + (common.to_str(sa[0]), self._remote_address[0], self._remote_address[1], self._server._listen_port)) raise Exception('IP %s is in forbidden list, reject' % common.to_str(sa[0])) if self._forbidden_portset: if sa[1] in self._forbidden_portset: - raise Exception('Port %d is in forbidden list, reject' % - sa[1]) + if self._remote_address: + raise Exception('Port %d is in forbidden list, when connect to %s:%d via port %d' % + (sa[1], self._remote_address[0], self._remote_address[1], self._server._listen_port)) + raise Exception('Port %d is in forbidden list, reject' % sa[1]) remote_sock = socket.socket(af, socktype, proto) self._remote_sock = remote_sock self._fd_to_handlers[remote_sock.fileno()] = self @@ -661,21 +666,20 @@ class TCPRelayHandler(object): else: data = obfs_decode[0] try: - newdata = self._protocol.server_post_decrypt(data) - '''if data and not newdata: - data = self._protocol.server_pre_encrypt(data) - data = self._encryptor.encrypt(data) - data = self._obfs.server_encode(data) + data, sendback = self._protocol.server_post_decrypt(data) + if sendback: + backdata = self._protocol.server_pre_encrypt('') + backdata = self._encryptor.encrypt(backdata) + backdata = self._obfs.server_encode(backdata) try: - self._write_to_sock(data, self._local_sock) + self._write_to_sock(backdata, self._local_sock) except Exception as e: shell.print_exception(e) if self._config['verbose']: traceback.print_exc() logging.error("exception from %s:%d" % (self._client_address[0], self._client_address[1])) self.destroy() - return''' - data = newdata + return except Exception as e: shell.print_exception(e) logging.error("exception from %s:%d" % (self._client_address[0], self._client_address[1]))