Creating New Process For Each Request On Ssl Socket Gives "typeerror: Cannot Serialize Socket Object", But Doing Same With Normal/non Ssl Socket Works
Solution 1:
I worked around this problem by accept the socket in the clear wrapping it with SSLContext within the child process. Everything I needed to create the SSLContext multiprocessing had no issues serializing.
UPDATE: The following is a server sudo code which illustrates the explanation above:
defclient_connection_handler(client_socket, client_address, ssl_settings):
context = ssl.SSLContext()
context.load_cert_chain(certfile=ssl_settings['certfile'], keyfile=ssl_settings['keyfile'],)
context.verify_mode = ssl_settings["verify_mode"]
context.load_verify_locations(cafile=ssl_settings["cafile"])
client_secured_socket = context.wrap_socket(client_socket, server_side=True)
## send and receive data#
client_secured_socket.close()
defserver():
server_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
server_socket.bind((hostname, port))
server_socket.listen(5)
whileTrue:
# Waiting for client connection
client_socket, client_address = server_socket.accept()
concurrent_connections = len(multiprocessing.active_children())
if max_concurrent_clients > concurrent_connections:
p = multiprocessing.Process(target=client_connection_handler, args=(client_socket, client_address, ssl_settings))
p.daemon = True
p.start()
continue# Max client connection has been reached
client_socket.close()
Solution 2:
I dont know whether I understood the exact reason, but I am stating it here.
Looking at following stacktrace lines:
17 ForkingPickler(file, protocol).dump(obj)
18 File "D:\Programs\python\python-3.6.6-amd64\lib\socket.py", line 185, in __getstate__
19 raise TypeError("Cannot serialize socket object")
20TypeError: Cannot serialize socket object
it seems that multiprocessing
module's Process.start()
method serializes the parameters passed to it for passing them to new process. And it further seems that SSLSocket
objects cannot be serialized. However, it seems that Socket
objects can be serialized. This issue states the same and thats why the Socket
based server works. However, I dont get why is this so (SSLSocket
is not serializable but Socket
objects can be serialized). I mean is there any method that is implemented by Socket
objects which are not implemented by SSLSocket
. Also note that the error occurs at socket.py, line 185, in __getstate__
, that is in Socket
class, but not in SSLSocket
class.
I will like if someone confirms above reason (that is SSLSocket
objects are not serializable and Socket
objects are serializable), explains exactly why is this the case and provides solution for using SSLSocket
with multiprocessing
module.
Workaround
I ended up forking new process using os.fork
. (Examples of os.fork
can be found here). Its supported on linux only. So, I installed python on cygwin and then used it.
Post a Comment for "Creating New Process For Each Request On Ssl Socket Gives "typeerror: Cannot Serialize Socket Object", But Doing Same With Normal/non Ssl Socket Works"