将空参数列表功能从C转换为C ++

时间:2018-06-25 22:07:02

标签: c++ c parameter-passing vxworks

我正在一个项目中尝试在C ++中编译VxWorks END。我认为我无法更改C ++的工作方式,而且我绝对不能对VxWorks进行太多更改。

除了一个问题外,这一切都很好。 VxWorks要求所有驱动程序在net_funcs结构体中注册其方法,该结构体具有以下字段(以及其他字段):

#ifdef __cplusplus
extern "C" {
#endif
...

typedef struct net_funcs
    {
    ...
    STATUS (*pollSend) (END_OBJ*, M_BLK_ID); /* Driver's polling send func. */
    STATUS (*pollRcv) (END_OBJ*, M_BLK_ID); /* Driver's polling recv func. */

    /*
     * The minimum required arguments for (*formAddress)() are:
     * (*formAddress)(M_BLK_ID, M_BLK_ID, M_BLK_ID, BOOL)
     */
    M_BLK_ID (*formAddress) ();           /* Driver's addr formation func. */

    /*
     * The minimum required arguments for (*packetDataGet)() are:
     * (*packetDataGet)(M_BLK_ID, LL_HDR_INFO *)
     */
    STATUS (*packetDataGet) ();           /* Driver's addr formation func. */
    ...
    } NET_FUNCS
...
#ifdef __cplusplus
}
#endif

请注意C样式的空参数列表。在C语言中,这意味着该字段可以是接受任何参数的函子。但是,在C ++中进行编译时,它将这些参数视为(void),然后在尝试实例化结构时引发错误。如果我尝试将参数更改为(first arg,...),传入默认的lib文件调用(endEtherAddressForm和endEtherPacketDataGet,均按照软件手册的建议从lib文件中调用)会导致错误,因为这些函子需要四个特定的参数,并且不接受可变数量的args。

我也许可以将其硬编码到默认函数的参数列表中,并希望达到最佳效果,但是在我这样做之前,是否有任何方法可以使此代码与C和C ++中的可变参数列表一起使用?还是我需要做一些事情才能使两个文件的外部“ C”结构起作用?

更新:

实例化该结构时,我使用以下代码:

LOCAL NET_FUNCS MBbufferNetFuncs =
    {
    ...
    MyCode::EndPollSend,
    MyCode::EndPollRcv,
    endEtherAddressForm, /* Library function from endLib.lib; declaration
        M_BLK_ID endEtherAddressForm(M_BLK_ID, M_BLK_ID, M_BLK_ID, BOOL)*/
    endEtherPacketDataGet /* Library function from endLib.lib; declaration
        STATUS endEtherAddressForm(M_BLK_ID, LL_HDR_INFO *)*/
    }

错误指出:

"A value of type "M_BLK_ID (*)(M_BLK_ID, M_BLK_ID, M_BLK_ID, BOOL)" cannot be used to initialize an entry of type "M_BLK_ID (*)()""

通常,人们会认为net_func声明开始处的extern“ C”声明可以防止出现空参数列表问题,但是事实并非如此。当我声明该结构的个人副本时,我不知道是否需要添加特殊代码,但是它似乎不起作用。

2 个答案:

答案 0 :(得分:0)

我无法测试您的设置,但是我发现(clang -Wpedantic)很满意:

extern "C" int f(...);
int r(int c) {
    return f(c) * c;
}
int main(void) { 
    return r(2);
}

它甚至可以工作,所以一定不要不确定行为... :) 但是,您需要执行以下操作:

ifdef __cplusplus
#define CLARGS ...
#else
#define CLARGS
#endif

然后进行声明:

M_BLK_ID (*formAddress) (CLARGS);

为防止C ++泄漏C代码。

答案 1 :(得分:0)

我对C和C ++有点生锈,但是如果可以使用内存...

函数参数的C语法为:

void foo1();              // Zero or more unspecified args
void foo2(int a, ...);    // One or more args
void foo3(void);          // No args

C ++语法为:

void bar1(...);           // Zero or more unspecified args
void bar2(int a, ...);    // One or more args
void bar3();              // No args