cpython icon indicating copy to clipboard operation
cpython copied to clipboard

ctypes: wrong exception message in docs

Open kamilturek opened this issue 3 years ago • 1 comments

Documentation

The ctypes docs say that the message of the ArgumentError for the presented example should be as follows: image

In fact, it looks like this:

>>> strchr = libc.strchr
>>> strchr.restype = c_char_p
>>> strchr.argtypes = [c_char_p, c_char]
>>> 
>>> strchr(b"abcdef", b"def")
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
ctypes.ArgumentError: argument 2: TypeError: wrong type

I will prepare a PR.

  • PR: gh-99267

kamilturek avatar Nov 08 '22 23:11 kamilturek

Note that the better error message from the c_set() set function gets cleared by PyCSimpleType_from_param() before it looks for an _as_parameter_ attribute on the object. We're left with the less useful message "wrong type". The original exception could be saved and then restored if the object doesn't have an _as_parameter_ attribute.

c_set(): https://github.com/python/cpython/blob/2eee9d9cd7eb1e396fa9a4af7c5fadeeafbdaa38/Modules/_ctypes/cfield.c#L1114-L1137

PyCSimpleType_from_param(): https://github.com/python/cpython/blob/2eee9d9cd7eb1e396fa9a4af7c5fadeeafbdaa38/Modules/_ctypes/_ctypes.c#L2208-L2274

Actually, I don't see why it doesn't first check for an _as_parameter_ attribute on value, and I don't see why it needs to recursively call PyCSimpleType_from_param().

eryksun avatar Nov 09 '22 00:11 eryksun

As per the docs, _as_parameter_ can return another object with the _as_parameter_ attribute. I believe that's why the recursion is needed.

The from_param() class method receives the Python object passed to the function call, it should do a typecheck or whatever is needed to make sure this object is acceptable, and then return the object itself, its as_parameter attribute, or whatever you want to pass as the C function argument in this case. Again, the result should be an integer, string, bytes, a ctypes instance, or an object with an as_parameter attribute.

https://docs.python.org/3/library/ctypes.html

kamilturek avatar Nov 24 '22 19:11 kamilturek

@eryksun I followed your suggestion of saving and restoring the exception. I opened a PR.

kamilturek avatar Nov 24 '22 20:11 kamilturek