Skip to content

Commit

Permalink
merge manyuser branch
Browse files Browse the repository at this point in the history
  • Loading branch information
breakwa11 committed Jun 26, 2015
1 parent e5b4a80 commit 1b0504a
Show file tree
Hide file tree
Showing 4 changed files with 61 additions and 16 deletions.
18 changes: 16 additions & 2 deletions shadowsocks/common.py
Original file line number Diff line number Diff line change
Expand Up @@ -138,6 +138,20 @@ def pack_addr(address):
address = address[:255] # TODO
return b'\x03' + chr(len(address)) + address

def pre_parse_header(data):
datatype = ord(data[0])
if datatype == 0x80 :
if len(data) <= 2:
return None
rand_data_size = ord(data[1])
if rand_data_size + 2 >= len(data):
logging.warn('header too short, maybe wrong password or '
'encryption method')
return None
data = data[rand_data_size + 2:]
elif datatype == 0x81:
data = data[1:]
return data

def parse_header(data):
addrtype = ord(data[0])
Expand Down Expand Up @@ -173,8 +187,8 @@ def parse_header(data):
else:
logging.warn('header is too short')
else:
logging.warn('unsupported addrtype %d, maybe wrong password' %
addrtype)
logging.warn('unsupported addrtype %d, maybe wrong password or '
'encryption method' % addrtype)
if dest_addr is None:
return None
return connecttype, to_bytes(dest_addr), dest_port, header_length
Expand Down
33 changes: 33 additions & 0 deletions shadowsocks/encrypt_test.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
from __future__ import absolute_import, division, print_function, \
with_statement

import sys
import os

sys.path.insert(0, os.path.join(os.path.dirname(__file__), '../'))


from crypto import rc4_md5
from crypto import openssl
from crypto import sodium
from crypto import table

def main():
print("\n""rc4_md5")
rc4_md5.test()
print("\n""aes-256-cfb")
openssl.test_aes_256_cfb()
print("\n""aes-128-cfb")
openssl.test_aes_128_cfb()
print("\n""rc4")
openssl.test_rc4()
print("\n""salsa20")
sodium.test_salsa20()
print("\n""chacha20")
sodium.test_chacha20()
print("\n""table")
table.test_encryption()

if __name__ == '__main__':
main()

18 changes: 6 additions & 12 deletions shadowsocks/tcprelay.py
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@
import random

from shadowsocks import encrypt, eventloop, shell, common
from shadowsocks.common import parse_header
from shadowsocks.common import pre_parse_header, parse_header

# we clear at most TIMEOUTS_CLEAN_SIZE timeouts each time
TIMEOUTS_CLEAN_SIZE = 512
Expand Down Expand Up @@ -320,12 +320,15 @@ def _handle_stage_addr(self, data):
logging.error('unknown command %d', cmd)
self.destroy()
return
data = pre_parse_header(data)
if data is None:
raise Exception('can not parse header')
header_result = parse_header(data)
if header_result is None:
raise Exception('can not parse header')
connecttype, remote_addr, remote_port, header_length = header_result
logging.info('%s connecting %s:%d from %s:%d' %
((connecttype == 0) and 'tcp' or 'udp',
((connecttype == 0) and 'TCP' or 'UDP',
common.to_str(remote_addr), remote_port,
self._client_address[0], self._client_address[1]))
self._remote_address = (common.to_str(remote_addr), remote_port)
Expand Down Expand Up @@ -356,15 +359,6 @@ def _handle_stage_addr(self, data):
# TODO use logging when debug completed
self.destroy()

def _has_ipv6_addr(self, addr_list):
for item in addr_list:
if type(item) is list:
if self._has_ipv6_addr(item):
return True
elif ':' in item:
return True
return False

def _create_remote_socket(self, ip, port):
if self._remote_udp:
addrs_v6 = socket.getaddrinfo("::", 0, 0, socket.SOCK_DGRAM, socket.SOL_UDP)
Expand Down Expand Up @@ -505,7 +499,7 @@ def _on_remote_read(self, is_remote_sock):
except Exception as e:
ip = socket.inet_pton(socket.AF_INET6, addr[0])
data = '\x00\x00\x00\x04' + ip + port + data
logging.info('udp recvfrom %s:%d %d bytes to %s:%d' % (addr[0], addr[1], len(data), self._client_address[0], self._client_address[1]))
logging.info('UDP recvfrom %s:%d %d bytes to %s:%d' % (addr[0], addr[1], len(data), self._client_address[0], self._client_address[1]))
else:
data = self._remote_sock.recv(BUF_SIZE)
except (OSError, IOError) as e:
Expand Down
8 changes: 6 additions & 2 deletions shadowsocks/udprelay.py
Original file line number Diff line number Diff line change
Expand Up @@ -70,7 +70,7 @@
import random

from shadowsocks import encrypt, eventloop, lru_cache, common, shell
from shadowsocks.common import parse_header, pack_addr
from shadowsocks.common import pre_parse_header, parse_header, pack_addr


BUF_SIZE = 65536
Expand Down Expand Up @@ -159,6 +159,10 @@ def _handle_server(self):
if not data:
logging.debug('UDP handle_server: data is empty after decrypt')
return
data = pre_parse_header(data)
if data is None:
return

header_result = parse_header(data)
if header_result is None:
return
Expand All @@ -173,7 +177,7 @@ def _handle_server(self):
client = self._cache.get(key, None)
if not client:
# TODO async getaddrinfo
logging.info('UDP handle_server %s:%d from %s:%d' % (common.to_str(server_addr), server_port, self._listen_addr, self._listen_port))
#logging.info('UDP handle_server %s:%d from %s:%d' % (common.to_str(server_addr), server_port, self._listen_addr, self._listen_port))
addrs = socket.getaddrinfo(server_addr, server_port, 0,
socket.SOCK_DGRAM, socket.SOL_UDP)
if addrs:
Expand Down

0 comments on commit 1b0504a

Please sign in to comment.