我正在研究一些我没有用pdb编写的代码。
(Pdb) self.function
<CFunctionType object at 0x000000DC768E0E18>
(Pdb) type(self.function)
<class 'ctypes.CFUNCTYPE.<locals>.CFunctionType'>
(Pdb) dir(self.function)
['__bool__', '__call__', '__class__', '__ctypes_from_outparam__', '__delattr__', '__dict__', '__dir__', '__doc__', '__eq__', '__format__', '__ge__', '__getattribute__', '__gt__', '__hash__', '__init__', '__le__', '__lt__', '__module__', '__ne__', '__new__', '__reduce__', '__reduce_ex__', '__repr__', '__setattr__', '__setstate__', '__sizeof__', '__str__', '__subclasshook__', '__weakref__', '_argtypes_', '_b_base_', '_b_needsfree_', '_flags_', '_objects', '_restype_', 'argtypes', 'errcheck', 'restype']
(Pdb) self.function._flags_
1
(Pdb) self.function._objects
{'0': <CDLL 'C:\path', handle 7ffe26465400 at 0xdc74ad2908>}
我是否有可能找出自定义函数的位置,或函数的名称是什么? self.function._objects指向一个DLL,但我不清楚我是如何找到该函数的名称所以我可以在源代码中查找它。
此外,是否可以在调用时进入函数?它在代码中以下列方式调用:
self.function(*self.args)
我有可能找出self.function的定义,
不,因为它是在一些用C(或其他语言)编写的源代码中定义的,你甚至没有(或许你可以,但Python不知道它在哪里);所有你拥有的是编译它的DLL / so / dylib。
......或者该功能的名称是什么?
是。您通常可以像Python中的许多其他对象一样获取ctypes C函数的名称:通过__name__
特殊属性:
>>> import ctypes
>>> libm = ctypes.CDLL('libm.dylib')
>>> fabs = libm.fabs
>>> fabs
<_FuncPtr object at 0x1067ac750>
>>> fabs.__name__
'fabs'
self.function._objects指向一个DLL,但我不清楚我是如何找到该函数的名称所以我可以在源代码中查找它。
你无法从那里获得功能名称。但是你可以通过_name
属性从那里获取库名:
>>> fabs._objects['0']._name
'libm.dylib'
(尽管有下划线,这是一个公共属性,正如文档解释的那样。)
这通常是传递给CDLL
构造函数或cdll.LoadLibrary
调用的名称。在Windows上,对于加载了cdll.spam
魔法的库,我认为你实际上得到了解决的路径名,比如'D:\path\to\spam.dll'
,而不仅仅是'spam'
或'spam.dll'
,但我不是正面的。
此外,是否可以在调用时进入函数?
不,因为函数是编译机器代码;它没有任何Python字节码供您介入。
当然,您可以附加一个像Visual Studio,lldb或gdb这样的调试器,并以这种方式进入机器代码。