[英]PInvoke struct with nested struct array
I'm trying to PInvoke a method which has a struct parameter with nested struct array pointer.我正在尝试 PInvoke 一个具有嵌套结构数组指针的结构参数的方法。 The c declaration looks like this:
c 声明如下所示:
duckdb_state duckdb_query(duckdb_connection connection, const char *query, duckdb_result *out_result);
typedef struct {
void *data;
bool *nullmask;
duckdb_type type;
char *name;
} duckdb_column;
typedef struct {
idx_t column_count;
idx_t row_count;
duckdb_column *columns;
char *error_message;
} duckdb_result;
I declared them in C# like this:我在 C# 中这样声明它们:
[DllImport("duckdb.dll", CallingConvention = CallingConvention.Cdecl, EntryPoint = "duckdb_query")]
public static extern DuckdbState DuckdbQuery(IntPtr connection, string query, out DuckdbResult result);
[StructLayout(LayoutKind.Sequential)]
public struct DuckdbColumn
{
IntPtr data;
bool nullmask;
DuckdbType type;
string name;
}
[StructLayout(LayoutKind.Sequential)]
public struct DuckdbResult
{
public long column_count;
public long row_count;
public IntPtr columns;
public string error_message;
}
But when I try to execute the query and read the columns I don't get any meaningful data:但是当我尝试执行查询并读取列时,我没有得到任何有意义的数据:
result = DuckdbQuery(connection, "SELECT * FROM integers", out queryResult);
DuckdbColumn[] columns = new DuckdbColumn[queryResult.column_count];
var queryResultColumns = queryResult.columns;
var columnPointer = Marshal.ReadIntPtr(queryResultColumns);
var ptrToStructure = (DuckdbColumn)Marshal.PtrToStructure(columnPointer, typeof(DuckdbColumn));
How should I change the PInvoke declarations so that I can read the columns after executign the query?我应该如何更改 PInvoke 声明,以便在执行查询后可以读取列?
There is example c code at: DuckDB c example有示例 c 代码: DuckDB c 示例
I can get column names with the following code:我可以使用以下代码获取列名:
for (int i = 0; i < queryResult.column_count; i++)
{
var column = (DuckdbColumn)Marshal.PtrToStructure(queryResult.columns + 8 + (Marshal.SizeOf<DuckdbColumn>() + 8) * i, typeof(DuckdbColumn));
columns[i] = column;
}
but type
field still says DUCKDB_TYPE_INVALID
但
type
字段仍然显示DUCKDB_TYPE_INVALID
As suggested by David in his answer I changed bool nullmask;
正如大卫在他的回答中所建议的,我改变了
bool nullmask;
to IntPtr nullmask;
到
IntPtr nullmask;
and I can now read column information like this:我现在可以读取这样的列信息:
for (int i = 0; i < queryResult.column_count; i++)
{
var column = (DuckdbColumn)Marshal.PtrToStructure(queryResult.columns + Marshal.SizeOf<DuckdbColumn>() * i, typeof(DuckdbColumn));
columns[i] = column;
}
You have translated this field incorrectly您错误地翻译了此字段
bool *nullmask
This is not a bool
it's a pointer.这不是一个
bool
它是一个指针。 Declare it as将其声明为
IntPtr nullmask;
There could be other errors because we can't see all the translations.可能还有其他错误,因为我们无法看到所有翻译。 Additionally, the
+8
in your array access pointer arithmetic looks suspicious.此外,数组访问指针算法中的
+8
看起来很可疑。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.