繁体   English   中英

我可以在导出到c的c ++函数中使用`bool`类型或不透明指针吗?

[英]Can I use `bool` type or opaque pointers to classes in a c++ function exported to c?

我正在编写我正在编写的库的API。 库本身将用c++编写,但API将使用extern "C"导出,以实现最佳的跨语言兼容性(稍后我将使用C#C++C和其他一些语言来使用此API)。
显然,API不能包含整个类或其他c++特定的功能(比如抛出异常),但我的问题是:

  1. 我可以在导出的API中使用bool类型吗? 毕竟,这是一个POD。
  2. 我可以使用类的不透明指针吗? 如果是这样,我将如何在头文件中声明它们,以便可以从C代码中使用头文件?

Bool应该没问题,ABI和语言设计人员对这些事情要谨慎(例如,C ++的complex<double>和C的complex double明确设计为兼容)。 可以使用前向声明将类转换为不透明指针。

#ifdef __cplusplus
class MyClass;
#else
#include <stdbool.h>
typedef struct MyClass MyClass;
extern "C" {
#endif

bool IsActivated(MyClass *p, int x);

#ifndef __cplusplus
}
#endif

请注意,如果设置了各种编译器标志或属性,我已经看到了ABI兼容性问题 - 例如,如果启用了结构打包,则bool在使用GCC 4.2的C和C ++中的大小不同。

  1. 我可以在导出的API中使用bool类型吗? 毕竟,这是一个POD。
  2. 我可以使用类的不透明指针吗?

我终于继续进行测试了。 以下是测试程序:

test_cpp.cpp:

#include "test.h"

class C {
    int a;
public:
    C() : a(42) {}
    int  getA() { return a; }
    void setA(int v) { a=v; }
};

int get7(bool b) { return b ? 7 : 3; }

C c;
C* getC() { return &c; }
int  getA(C* t) { return t->getA(); }
void setA(C* t, int v) { return t->setA(v); }

test_c.c:

#include <stdio.h>
#include "test.h"

int main()
{
    C* c = getC();
    printf("%d\n", getA(c));
    setA(c, 10);
    printf("%d\n", getA(c));
    printf("%d\n%d\n%d\n%d\n", get7(0), get7(1), get7(2), get7(-1));

    return 0;
}

test.h:

#ifdef __cplusplus
extern "C" {
#else
#define bool _Bool
#endif

struct C;
typedef struct C C;

int get7(bool b);

C* getC();
int  getA(C* t);
void setA(C* t, int v);

#ifdef __cplusplus
}
#endif

在windows上使用mingw64 gcc-4.9.0进行编译

gcc -c test_c.c
g++ test_cpp.cpp test_c.o

它编译并正确运行。 兴趣点:

  • g++完全没有问题, C被声明为struct ,后来定义为class
  • c ++ boolc _Bool可互换使用

我尝试使用MS编译器(VS2012),除了一个我无法解释的小细节外,它的工作方式相同:在头文件中,我不得不改变

int get7(bool b);

int get7(bool);

让它编译。 如果有人能够解释这一点,我很乐意理解它。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM