extern "C"的作用
extern "C"在C++代码中是为了告诉编译器禁止Name Mangling(标识符重命名)。 ——参考博客
1. C++中的Name Mangling
根据 Wiki ,C++具有函数重载功能,也就是同名但参数不同的多个函数,所以C++编译器编译时会有Name Mangling操作,根据参数特点为函数生成新的标识符。
例如,下面代码中两个函数编译后的名称可能为: ——参考知乎,使用objdump可以反汇编出函数标识符
__Z3adddd,表示参数列表为两个double类型的add函数,(3代表函数名称是3个字符).
__Z3addii,表示参数列表为两个int类型的add函数。
int add(int a, int b) { return a+b; } double add(double a, double b) { return a+b; }
但是,C++的Name Mangling没有统一标准,各个厂商的编译器的重命名方法不一样,编译生成的对象文件在不同平台可能无法通用,有的函数会找不到,undefined symbol。
2. C中的Name Mangling
C标准规定了Name-Mangling的规范,任何一个支持C语言的编译器,它编译出来的obj文件可以共享,链接成可执行文件。
这是一种标准,如果DLL跟其使用者都采用这种约定,那么就可以解决函数重命名规则不一致导致的错误。
3. 有如下几种等效的使用方法
注意,extern "C" 应当放在#include、using namespace等部分之后。
1)用花括号包住需要处理的函数
#include <iostream> using namespace std; extern "C" { int get_word(int a=0) { return a-1; } int get2(int a, int b){ return a+b; } }
2)在需要处理的函数声明前加一句声明
#include <iostream> using namespace std; extern "C" int get_word(int a=0) { return a-1; } extern "C" int get2(int a, int b){ return a+b; }
3)
#include <iostream> using namespace std; extern "C" { int get_word(int); int get2(int, int); } int get_word(int a=0) { return a-1; } int get2(int a, int b){ return a+b; }