SystemError: PY_SSIZE_T_CLEAN macro must be defined for '#' formats

Viewed 5937

I cannot find anything on this. I'm getting error:

Traceback (most recent call last):
  File "/path/to/pwdb.py", line 265, in <module>
    password_db()
  File "/path/to/pwdb.py", line 73, in __init__
    self.cipher = AES.new(key,AES.MODE_ECB)
  File "/home/STACKOVERFLOW/.local/lib/python3.10/site-packages/Crypto/Cipher/AES.py", line 95, in new
    return AESCipher(key, *args, **kwargs)
  File "/home/STACKOVERFLOW/.local/lib/python3.10/site-packages/Crypto/Cipher/AES.py", line 59, in __init__
    blockalgo.BlockAlgo.__init__(self, _AES, key, *args, **kwargs)
  File "/home/STACKOVERFLOW/.local/lib/python3.10/site-packages/Crypto/Cipher/blockalgo.py", line 141, in __init__
    self._cipher = factory.new(key, *args, **kwargs)
SystemError: PY_SSIZE_T_CLEAN macro must be defined for '#' formats

I'm pretty sure the line it's getting the error from is:

self.cipher = AES.new(key,AES.MODE_ECB)

The script was working not too long ago. Did PyCrypto update its formatting or something ? And does anyone have any idea on how to fix this ? I can provide more of the code if need be.

4 Answers

It sounds like the extension was not updated for python 3.10.

On 3.10 any module(s) that use the # variant when parsing arguments need to have a #define PY_SSIZE_T_CLEAN before including Python.h.

From the docs:

For all # variants of formats (s#, y#, etc.), the macro PY_SSIZE_T_CLEAN must be defined before including Python.h. On Python 3.9 and older, the type of the length argument is Py_ssize_t if the PY_SSIZE_T_CLEAN macro is defined, or int otherwise.

See https://docs.python.org/3/c-api/arg.html#strings-and-buffers

You can use pycryptodome python package instead of pycrypto. Pycryptodome seems to have replaced the currently not maintained pycrypto package and works as is with the python 3.10 related changes as well.

I might have fixed it for AES, pretty sure I fixed it for RIPEMD160, as my slotmachine code is now running on termux, and it wasn't before. The code changes are at https://github.com/jcomeauictx/pycrypto/commit/38e5ebbf98fea96cf67b354e13fef7d1959ec34a, and you can install it using pip install git+https://github.com/jcomeauictx/pycrypto. Note that I haven't made any attempt to fix any security issues in the pycrypto code, I only addressed this PY_SSIZE_T_CLEAN problem.

uninstall pycryto and install pycryptodome

pip uninstall pycrypto
pip install pycryptodome
Related