更新在 C DLL 中创建的 LP_c_ubyte 缓冲区
Updating an LP_c_ubyte buffer created in a C DLL
我正在使用 Python ctypes 为 C DLL 创建一个 Python 包装器。
在下面的 Python 代码中,我创建了一个 connectionString
的 c_ubyte
数组,我需要用它来填充个人。例如 1,2,3,4,5,6... 这个连接字符串被传递给 DLL 的 DoCallBack
函数并打印出来。为回调函数创建一个缓冲区来填充,并将所有内容传递给 python 回调函数。
- 我正在寻找一种方法来更新
connectionString
字节,然后再将它们传递给 DLL 的 DoCallBack
。
- 然后如何从python
callbackFnk
函数中提取connectionString
的字节。
- 我正在寻找一种方法来从
callbackFnk
python 函数 中更新 outBuffer
中的字节
这个问题的延续
C DLL 代码
typedef void(*FPCallback)(unsigned char * outBuffer, unsigned short MaxOutBufferLength, unsigned char * connectionString);
FPCallback g_Callback;
extern "C" __declspec( dllexport ) void RegisterCallback(void(*p_Callback)( unsigned char * outBuffer, unsigned short MaxOutBufferLength, unsigned char * connectionString)) {
g_Callback = p_Callback ;
}
extern "C" __declspec( dllexport ) void DoCallBack( unsigned char connectionString) {
printf( "connectionString=[%02x %02x %02x %02x %02x %02x...]\n", connectionString[0], connectionString[1], connectionString[2], connectionString[3], connectionString[4], connectionString[5] );
const unsigned short MAX_BUFFER_SIZE = 6 ;
unsigned char outBuffer[MAX_BUFFER_SIZE];
g_Callback( outBuffer, MAX_BUFFER_SIZE, connectionString, 6 );
// Print the results.
printf( "buffer=[%02x %02x %02x %02x %02x %02x...]\n", buffer[0], buffer[1], buffer[2], buffer[3], buffer[4], buffer[5] );
}
Python代码
def callbackFnk( outBuffer, outBufferMaxSize, connectionString )
# (Q2) How do I extract individual bytes of the connectionString?
# (Q3) How do I update individual bytes of the out buffer?
customDLL = cdll.LoadLibrary ("customeDLL.dll")
# RegisterCallback
CustomDLLCallbackFUNC = CFUNCTYPE(None, POINTER( c_ubyte), c_ushort, POINTER( c_ubyte) )
CustomDLLCallback_func = CustomDLLCallbackFUNC( callbackFnk )
RegisterCallback = customDLL.RegisterCallback
RegisterCallback.argtypes = [ CustomDLLCallbackFUNC ]
RegisterCallback( CustomDLLCallback_func )
# DoCallBack
DoCallBack = customDLL.DoCallBack
DoCallBack.argtypes = [ POINTER( c_ubyte) ]
connectionString = c_ubyte(6)
# (Q1) How do I update this array of bytes?
# Call the callback
DoCallBack(connectionString)
OP的例子有很多错误,无法编译,所以我把它放在一起。我假设 connectionString
只是一个以 nul 结尾的输入字符串,并演示了在回调中更新输出字符串。
请注意,对于 输入 字符串,c_char_p
可以是类型,并且可以传递 Python 字节字符串。 c_wchar_p
用于 Python Unicode 字符串。不得在 C 代码中修改该字符串。回调也会将其作为 Python 字符串接收,使其易于阅读。
输出缓冲区可以被索引,注意不要索引超过缓冲区的长度。调用者分配的输出缓冲区应始终作为指针和长度传递。
C++ DLL
#include <stdio.h>
typedef void (*CALLBACK)(const char* string, unsigned char* buffer, size_t size);
CALLBACK g_pCallback;
extern "C" __declspec(dllexport) void RegisterCallback(CALLBACK pCallback) {
g_pCallback = pCallback;
}
extern "C" __declspec(dllexport) void DoCallBack(char* string) {
unsigned char buf[6];
printf("string = %s\n", string);
g_pCallback(string, buf, sizeof(buf));
printf("buf = [%02x %02x %02x %02x %02x %02x]\n", buf[0], buf[1], buf[2], buf[3], buf[4], buf[5]);
}
Python
from ctypes import *
CALLBACK = CFUNCTYPE(None,c_char_p,POINTER(c_ubyte),c_size_t)
@CALLBACK
def callback(string,buf,length):
print(string)
for i in range(length):
buf[i] = i * 2
dll = CDLL('test')
# RegisterCallback
RegisterCallback = dll.RegisterCallback
RegisterCallback.argtypes = [CALLBACK]
RegisterCallback.restype = None
RegisterCallback(callback)
# DoCallBack
DoCallBack = dll.DoCallBack
DoCallBack.argtypes = [c_char_p]
DoCallBack.restype = None
DoCallBack(b'test string')
输出
string = test string
b'test string'
buf = [00 02 04 06 08 0a]
我正在使用 Python ctypes 为 C DLL 创建一个 Python 包装器。
在下面的 Python 代码中,我创建了一个 connectionString
的 c_ubyte
数组,我需要用它来填充个人。例如 1,2,3,4,5,6... 这个连接字符串被传递给 DLL 的 DoCallBack
函数并打印出来。为回调函数创建一个缓冲区来填充,并将所有内容传递给 python 回调函数。
- 我正在寻找一种方法来更新
connectionString
字节,然后再将它们传递给 DLL 的DoCallBack
。 - 然后如何从python
callbackFnk
函数中提取connectionString
的字节。 - 我正在寻找一种方法来从
callbackFnk
python 函数 中更新
outBuffer
中的字节
这个问题的延续
C DLL 代码
typedef void(*FPCallback)(unsigned char * outBuffer, unsigned short MaxOutBufferLength, unsigned char * connectionString);
FPCallback g_Callback;
extern "C" __declspec( dllexport ) void RegisterCallback(void(*p_Callback)( unsigned char * outBuffer, unsigned short MaxOutBufferLength, unsigned char * connectionString)) {
g_Callback = p_Callback ;
}
extern "C" __declspec( dllexport ) void DoCallBack( unsigned char connectionString) {
printf( "connectionString=[%02x %02x %02x %02x %02x %02x...]\n", connectionString[0], connectionString[1], connectionString[2], connectionString[3], connectionString[4], connectionString[5] );
const unsigned short MAX_BUFFER_SIZE = 6 ;
unsigned char outBuffer[MAX_BUFFER_SIZE];
g_Callback( outBuffer, MAX_BUFFER_SIZE, connectionString, 6 );
// Print the results.
printf( "buffer=[%02x %02x %02x %02x %02x %02x...]\n", buffer[0], buffer[1], buffer[2], buffer[3], buffer[4], buffer[5] );
}
Python代码
def callbackFnk( outBuffer, outBufferMaxSize, connectionString )
# (Q2) How do I extract individual bytes of the connectionString?
# (Q3) How do I update individual bytes of the out buffer?
customDLL = cdll.LoadLibrary ("customeDLL.dll")
# RegisterCallback
CustomDLLCallbackFUNC = CFUNCTYPE(None, POINTER( c_ubyte), c_ushort, POINTER( c_ubyte) )
CustomDLLCallback_func = CustomDLLCallbackFUNC( callbackFnk )
RegisterCallback = customDLL.RegisterCallback
RegisterCallback.argtypes = [ CustomDLLCallbackFUNC ]
RegisterCallback( CustomDLLCallback_func )
# DoCallBack
DoCallBack = customDLL.DoCallBack
DoCallBack.argtypes = [ POINTER( c_ubyte) ]
connectionString = c_ubyte(6)
# (Q1) How do I update this array of bytes?
# Call the callback
DoCallBack(connectionString)
OP的例子有很多错误,无法编译,所以我把它放在一起。我假设 connectionString
只是一个以 nul 结尾的输入字符串,并演示了在回调中更新输出字符串。
请注意,对于 输入 字符串,c_char_p
可以是类型,并且可以传递 Python 字节字符串。 c_wchar_p
用于 Python Unicode 字符串。不得在 C 代码中修改该字符串。回调也会将其作为 Python 字符串接收,使其易于阅读。
输出缓冲区可以被索引,注意不要索引超过缓冲区的长度。调用者分配的输出缓冲区应始终作为指针和长度传递。
C++ DLL
#include <stdio.h>
typedef void (*CALLBACK)(const char* string, unsigned char* buffer, size_t size);
CALLBACK g_pCallback;
extern "C" __declspec(dllexport) void RegisterCallback(CALLBACK pCallback) {
g_pCallback = pCallback;
}
extern "C" __declspec(dllexport) void DoCallBack(char* string) {
unsigned char buf[6];
printf("string = %s\n", string);
g_pCallback(string, buf, sizeof(buf));
printf("buf = [%02x %02x %02x %02x %02x %02x]\n", buf[0], buf[1], buf[2], buf[3], buf[4], buf[5]);
}
Python
from ctypes import *
CALLBACK = CFUNCTYPE(None,c_char_p,POINTER(c_ubyte),c_size_t)
@CALLBACK
def callback(string,buf,length):
print(string)
for i in range(length):
buf[i] = i * 2
dll = CDLL('test')
# RegisterCallback
RegisterCallback = dll.RegisterCallback
RegisterCallback.argtypes = [CALLBACK]
RegisterCallback.restype = None
RegisterCallback(callback)
# DoCallBack
DoCallBack = dll.DoCallBack
DoCallBack.argtypes = [c_char_p]
DoCallBack.restype = None
DoCallBack(b'test string')
输出
string = test string
b'test string'
buf = [00 02 04 06 08 0a]