pyOpenSSL SSL3_WRITE_PENDING:bad write retry, return self._sslobj.write(data) error: [Errno 10054]

ぐ巨炮叔叔 提交于 2020-01-05 08:02:28

问题


I'm now developing a chatting server in Python. I am in the middle of applying pyOpenSSL to the chatting server and dummy clients which I made for testing. But whenever sending text messages and photo file from dummy clients to the server, pyOpenSSL returns significant error which drives me to stop using pyOpenSSL like below.

send_text_message() : exception : [Errno 1] _ssl.c:1309: error:1409F07F:SSL routines:SSL3_WRITE_PENDING:bad write retry
send_text_message() : exception : [Errno 1] _ssl.c:1309: error:1409F07F:SSL routines:SSL3_WRITE_PENDING:bad write retry
send_text_message() : exception : [Errno 1] _ssl.c:1309: error:1409F07F:SSL routines:SSL3_WRITE_PENDING:bad write retry
send_text_message() : exception : [Errno 1] _ssl.c:1309: error:1409F07F:SSL routines:SSL3_WRITE_PENDING:bad write retry
send_text_message() : exception : [Errno 1] _ssl.c:1309: error:1409F07F:SSL routines:SSL3_WRITE_PENDING:bad write retry
send_text_message() : exception : [Errno 1] _ssl.c:1309: error:1409F07F:SSL routines:SSL3_WRITE_PENDING:bad write retry
send_text_message() : exception : [Errno 1] _ssl.c:1309: error:1409F07F:SSL routines:SSL3_WRITE_PENDING:bad write retry

Could you let me know how to solve the error? there's one more error which causes dummy client to die.

[client1|chatting1A] socket closed : device_id : client1, client_chatting_id : chatting1A, error : [Errno 10053] 
Exception in thread Thread-8:
Traceback (most recent call last):
  File "C:\Python27\lib\threading.py", line 810, in __bootstrap_inner
    self.run()
  File "C:\Python27\lib\threading.py", line 1082, in run
    self.function(*self.args, **self.kwargs)
  File "D:\temp\uTok1\uTokSocketServer\com\rurusoft\utok\DummyClient.py", line 97, in send_photo_message
    sock.write(message)
  File "C:\Python27\lib\ssl.py", line 172, in write
    return self._sslobj.write(data)
error: [Errno 10054]

Without pyOpenSSL, dummy clients and the server work well. Applying pyOpenSSL causes unexpected problems :(. If you have encountered the problems or have solutions to the problems, please let me know. .... If there's no solutions to the error, I'd rather find out other alternatives not using OpenSSL.. Or do you know any alterntives which can encrypt/decrypt chatting messages and personal files transfered between machines?

Though I already stored data to be sent in a local variable before writing(sending) the data, the error happens everytime.


  json_encoded = json.dumps(data)
          while True:
              try:
                  sock.write(json_encoded)
                  break
              except Exception, e:
                  Log.print_log(self.LOG_TAG, 'send_text_message() : exception : %s' % (e))
                  time.sleep(0.05)

Solved : As @David Schwartz commented, the following codes solved the upper issues.

    import StringIO
    ...
    io = StringIO.StringIO()
    io.write(json.dumps(data))
    buffer = io.getvalue()
    while True:
        try:
            sock.write(buffer)
            break
    ...
    

回答1:


OpenSSL has very strict requirements about how writes can be retried -- specifically the buffer's address and contents must not be changed. When you retry a write, you must retry with the exact same buffer (the same contents are not sufficient and, of course, different contents is absolutely prohibited).

For example, this is broken:

ssl_socket.send(send_buffer.getvalue())

Since you didn't store the value you passed to send, if you need to retry the send, how can you pass it the same value? There's no guarantee a subsequent call to getvalue will return the same result. Repeating this operation can generate a bad write retry if the buffer moves, which it can at any time.

Update: Your code does nothing to prevent the buffer from changing. There is no object that does not change that reflects the buffer. Try:

io = StringIO()
json.dumps(data, io)
buffer = io.getvalue()

      while True:
          try:
              sock.write(buffer)
              break

Here, io is the buffer, and getvalue is called on it only once.



来源:https://stackoverflow.com/questions/20715408/pyopenssl-ssl3-write-pendingbad-write-retry-return-self-sslobj-writedata-er

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!