def catch(self, flower, deflector): DEBUG_POSITION = 'Symbiosis_Bee:Bee:Catch:' data_flower = b'' data_deflector = b'' key_data = b'' keys = [] aes_recv = None timeout = TIMEOUT while self.alive: # (read, _, exception) = select.select([flower, deflector], [], [flower, deflector], timeout) (read, _, exception) = select.select([flower], [], [flower], timeout) if exception: if DEBUG: print(DEBUG_POSITION, 'select exception이 발생했습니다:') if DEBUG: print(exception) return elif read: for i in read: if i == flower: try: # Receive Data data_flower = data_flower + i.recv(1024) if len(data_flower) >= 1024: # Raw Cell raw_cell, data_flower = data_flower[0:1024], data_flower[1024:] # Decode Cell cell = decodeCell(raw_cell) #printCell(cell) if cell['type'] == SYMBIOSIS_CELL_TYPE_RESPONSE: # Decrypt data = cell['data'] decrypted = b'' while len(data) >= 16: decrypted = decrypted + aes_recv.decrypt(data[:16]) data = data[16:] decrypted = decrypted + data # Digest digest = SHA256.new(decrypted + keys[2]).digest() if digest != cell['digest']: continue # Send Data self.stream.send(cell['streamID'], decrypted) elif cell['type'] == SYMBIOSIS_CELL_TYPE_REQUEST: # Flower Request print('FLOWER REQ > BEE > DEFLECTOR:') #printCell(cell) deflector.send(raw_cell) pass elif cell['type'] == SYMBIOSIS_CELL_TYPE_KEY_REQUEST: # Flower Key Request #deflector.send(raw_cell) pass elif cell['type'] == SYMBIOSIS_CELL_TYPE_KEY_RESPONSE: # crt:1099, g_y:512, sig:256, h_k:32 key_data = key_data + cell['data'] if cell['streamID'] == 0: continue # split crt = key_data[:1099] g_y = key_data[1099:1099+512] sig = (int.from_bytes(key_data[1099+512:1099+512+256], byteorder='big'), ) h_k = key_data[1099+512+256:] key_data = b'' # get public key from crt pem = crt.decode('utf-8') lines = pem.replace(" ",'').split() der = a2b_base64(''.join(lines[1:-1]).encode('ascii')) cert = DerSequence() cert.decode(der) tbsCertificate = DerSequence() tbsCertificate.decode(cert[0]) subjectPublicKeyInfo = tbsCertificate[5] puk = RSA.importKey(subjectPublicKeyInfo) # verify hash = SHA256.new(g_y).digest() if puk.verify(hash, sig): print("Key Exchange: Verify") self.dh.genKey(int.from_bytes(g_y, byteorder='big')) # h.digest() = SHA256.new(K).digest() K = self.dh.getKey() h = hashlib.sha256() h.update(str(K).encode(encoding='utf_8', errors='strict')) if h_k == h.digest(): print("Key Exchange: Complete") K = self.dh.getKey() aes = AES.new(K, AES.MODE_ECB) # Keys for i in range(4): keys = keys + [ str(i).encode() + K[1:] ] aes_recv = AES.new(keys[3], AES.MODE_ECB) aes_send = AES.new(keys[1], AES.MODE_ECB) self.exchange = True else: print("Key Exchange: Retry") data = self.dh.publicKey.to_bytes((self.dh.publicKey.bit_length() + 7) // 8, 'big') self.flower.send(encodeCell(SYMBIOSIS_CELL_TYPE_KEY_REQUEST, len(data), 0, bytes(32), data)) else: print("Key Exchange: Retry") data = self.dh.publicKey.to_bytes((self.dh.publicKey.bit_length() + 7) // 8, 'big') self.flower.send(encodeCell(SYMBIOSIS_CELL_TYPE_KEY_REQUEST, len(data), 0, bytes(32), data)) except socket.error as e: if DEBUG: print(DEBUG_POSITION, '알 수 없는 오류가 발생했습니다:flower') if DEBUG: print(e) return elif i == deflector: try: # Receive Data data_deflector = data_deflector + i.recv(1024) if len(data_deflector) >= 1024: # Raw Cell raw_cell, data_deflector = data_deflector[0:1024], data_deflector[1024:] # Deflector Response print('DEFLECTOR RES > BEE > FLOWER') flower.send(raw_cell) except socket.error as e: if DEBUG: print(DEBUG_POSITION, '알 수 없는 오류가 발생했습니다:deflector') if DEBUG: print(e) return if self.exchange == True: self.stream.select(flower, SYMBIOSIS_CELL_TYPE_REQUEST, aes_send, keys[0])
def handle(self, flower): DEBUG_POSITION = 'Symbiosis_Server:Server:Handle:' dh = DiffieHellman() data_proxy = b'' keys = [] aes_recv = None timeout = TIMEOUT while self.running: (read, _, exception) = select.select([flower], [], [flower], timeout) if exception: if DEBUG: print(DEBUG_POSITION, 'select exception이 발생했습니다:') if DEBUG: print(exception) return elif read: for i in read: try: # Receive Data data_proxy = data_proxy + i.recv(1024) if len(data_proxy) >= 1024: # Raw Cell raw_cell, data_proxy = data_proxy[0:1024], data_proxy[1024:] # Decode Cell cell = decodeCell(raw_cell) if cell['type'] == SYMBIOSIS_CELL_TYPE_REQUEST: # Decrypt data = cell['data'] decrypted = b'' while len(data) >= 16: decrypted = decrypted + aes_recv.decrypt(data[:16]) data = data[16:] decrypted = decrypted + data # Digest digest = SHA256.new(decrypted + keys[0]).digest() if digest != cell['digest']: continue # Connect to Squid with streamID if not cell['streamID'] in self.stream.streams.keys(): if self.stream.connect('localhost', 3128, cell['streamID']) == False: if DEBUG: print(DEBUG_POSITION, 'Squid에 연결할 수 없습니다.') continue # Send Data self.stream.send(cell['streamID'], decrypted) elif cell['type'] == SYMBIOSIS_CELL_TYPE_KEY_REQUEST: print("Key Exchange: Start") # g_x g_x = cell['data'] # g_y g_y = dh.publicKey.to_bytes((dh.publicKey.bit_length() + 7) // 8, 'big') # H(K) dh.genKey(int.from_bytes(g_x, byteorder='big')) K = dh.getKey() # h_k = SHA256.new(K.decode('utf-8')).digest() h = hashlib.sha256() h.update(str(K).encode(encoding='utf_8', errors='strict')) h_k = h.digest() # certificate crt = open("./ss.crt").read().encode() # sig = sign(SHA256(g_y)) prk = RSA.importKey(open('private.key','r').read()) hash = SHA256.new(g_y).digest() n = int(prk.sign(hash, '')[0]) sig = n.to_bytes((n.bit_length() + 7) // 8, 'big') # Keys for i in range(4): keys = keys + [ str(i).encode() + K[1:] ] aes_recv = AES.new(keys[1], AES.MODE_ECB) aes_send = AES.new(keys[3], AES.MODE_ECB) # crt:1099, g_y:512, sig:256, h_k:32 data = crt + g_y + sig + h_k while len(data) > 0: if len(data) <= 987: end = 1 else: end = 0 flower.send(encodeCell(SYMBIOSIS_CELL_TYPE_KEY_RESPONSE, len(data[:987]), end, bytes(32), data[:987])) data = data[987:] self.exchange = True print('Key Exchange: End') except socket.error as e: if DEBUG: print(DEBUG_POSITION, '알 수 없는 오류가 발생했습니다:') if DEBUG: print(e) return if self.exchange == True: self.stream.select(flower, SYMBIOSIS_CELL_TYPE_RESPONSE, aes_send, keys[2])