调用一个C函数,该函数接受来自Nim的struct指针(Call a C function that accepts a const pointer to struct from Nim)

编程入门 行业动态 更新时间:2024-10-24 19:19:52
调用一个C函数,该函数接受来自Nim的struct指针(Call a C function that accepts a const pointer to struct from Nim)

我使用其外部函数接口从Nim使用GNU argparse。 在<argp.h>中有函数argp_parse,声明如下

extern error_t argp_parse (const struct argp *__restrict __argp, int __argc, char **__restrict __argv, unsigned __flags, int *__restrict __arg_index, void *__restrict __input);

棘手的部分是第一个参数之前的const和__restrict,在Nim中我编写了这段代码

type ArgpChild {.importc: "struct argp_child"} = object argp : ptr[Argp] flags : cint header : cstring group : cint Argp* {.importc: "struct argp", header: "<argp.h>"} = object options : ptr[ArgpOption] parser : pointer #proc (key : cint, arg: cstring, state : ptr[ArgpState]) : Error args_doc : cstring doc : cstring children : ArgpChild help_filter : pointer #proc(key : int, text : cstring, input: pointer) : cstring argp_domain : cstring ArgpOption* {.importc: "struct argp_option"} = object name : cstring key : cint arg : cstring flags : cint doc : cstring group : cint ArgpState {.importc: "struct argp_state"} = object input : pointer Error* = enum ARGP_KEY_ARG = 0, ARGP_ERR_UNKNOWN = 7, ARGP_KEY_END = 0x1000001 proc argp_parse*(argp : Argp, argc : cint, argv : cstringArray, flags: cuint, arg_index: ptr[cint], input : pointer) : Error {.importc: "argp_parse".}

问题是Nim编译器(带有c后端)为argp_parse函数生成这一行(注意第一个参数之前缺少的const和__restrict关键字)

N_CDECL(Error177010, argp_parse)(struct argp* argp0, int argc0, NCSTRING* argv0, unsigned int flags0, int* argindex0, void* input0);

然后,当gcc处理该文件时,它会抱怨“argp_parse'的冲突类型”,我猜这是因为它在第一个参数中找到了具有不同类型的相同函数的两个定义。

有没有办法强制Nim编译器在使用c后端时在函数参数之前添加const(也许__restrict)关键字?

I am using GNU argparse from Nim using its foreign function interface. In <argp.h> there is function argp_parse which is declared as follows

extern error_t argp_parse (const struct argp *__restrict __argp, int __argc, char **__restrict __argv, unsigned __flags, int *__restrict __arg_index, void *__restrict __input);

the tricky part are the const and __restrict before the first parameter, in Nim I wrote this code

type ArgpChild {.importc: "struct argp_child"} = object argp : ptr[Argp] flags : cint header : cstring group : cint Argp* {.importc: "struct argp", header: "<argp.h>"} = object options : ptr[ArgpOption] parser : pointer #proc (key : cint, arg: cstring, state : ptr[ArgpState]) : Error args_doc : cstring doc : cstring children : ArgpChild help_filter : pointer #proc(key : int, text : cstring, input: pointer) : cstring argp_domain : cstring ArgpOption* {.importc: "struct argp_option"} = object name : cstring key : cint arg : cstring flags : cint doc : cstring group : cint ArgpState {.importc: "struct argp_state"} = object input : pointer Error* = enum ARGP_KEY_ARG = 0, ARGP_ERR_UNKNOWN = 7, ARGP_KEY_END = 0x1000001 proc argp_parse*(argp : Argp, argc : cint, argv : cstringArray, flags: cuint, arg_index: ptr[cint], input : pointer) : Error {.importc: "argp_parse".}

the problem is that the Nim compiler (with c backend) generates this line for argp_parse function (note the missing const and __restrict keywords before the first parameter)

N_CDECL(Error177010, argp_parse)(struct argp* argp0, int argc0, NCSTRING* argv0, unsigned int flags0, int* argindex0, void* input0);

then, when gcc handles that file, it complains yelling "conflicting types for ‘argp_parse’", I guess this is because it finds two definitions of the same functions with different types in the first parameter.

Is there any way to force the Nim compiler to add the const (and maybe __restrict) keyword before a function parameter when using the c backend?

最满意答案

Nim将来会支持一个restrict编译指示,允许您指定这些参数。 从Nim存储库中最新的todo.txt可以看出这一点。

与此同时,有一种可能的解决办法。 您可以使用emit pragma而不是importc pragma:

proc argp_parse*(argp: Argp, argc: cint, argv: cstringArray, flags: cuint, arg_index: ptr[cint], input: pointer): Error = {.emit: "argp_parse(`argp`, `argc`, `argv`, `flags`, `arg_index`, `input`);".}

这将创建一个常规的非导入过程,只转发调用argp_parse函数。

Nim will support a restrict pragma in the future that will allow you to specify such parameters. This is evident from the latest todo.txt in the Nim's repository.

In the meantime, there is one possible work-around for this. Instead of using the importc pragma, you can use the emit pragma:

proc argp_parse*(argp: Argp, argc: cint, argv: cstringArray, flags: cuint, arg_index: ptr[cint], input: pointer): Error = {.emit: "argp_parse(`argp`, `argc`, `argv`, `flags`, `arg_index`, `input`);".}

This will create a regular non-imported proc that just forwards the call the argp_parse function.

更多推荐

本文发布于:2023-07-29 18:31:00,感谢您对本站的认可!
本文链接:https://www.elefans.com/category/jswz/34/1318652.html
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。
本文标签:函数   指针   Nim   struct   Call

发布评论

评论列表 (有 0 条评论)
草根站长

>www.elefans.com

编程频道|电子爱好者 - 技术资讯及电子产品介绍!