命名空间嵌套函数的最佳实践和语义以及extern的使用;"; 我正在创建一个带有C-ABI接口的C++库。
这是GCC处理外部“C”限定符的方式:命名空间嵌套函数的最佳实践和语义以及extern的使用;"; 我正在创建一个带有C-ABI接口的C++库。,c++,portability,abi,C++,Portability,Abi,这是GCC处理外部“C”限定符的方式: namespace x { extern "C" int monkey(int x) { return 1; } int chimpanzee(int x) { return 1; } } 相关的nm输出: 00000000004005cd T _ZN1x10chimpanzeeEi 00000000004005bf T monkey 问题: 我希望将C-ABI中涉及的函数留在名称空间
namespace x {
extern "C" int monkey(int x) {
return 1;
}
int chimpanzee(int x) {
return 1;
}
}
相关的nm
输出:
00000000004005cd T _ZN1x10chimpanzeeEi
00000000004005bf T monkey
问题:
我希望将C-ABI中涉及的函数留在名称空间中,以获得最大的重用灵活性重要注意事项:编译库后,我会给链接器一个映射文件(GCC)或模块定义文件(MSVC)
你所做的很好,会给你想要的效果。从C++编程语言,第三版,第208页:“一个名字有C链接的名字可以在命名空间中声明。命名空间会影响C++程序中名字的访问方式,但不是链接器看到它的方式。<代码> Prtff())/<代码>从代码> STD< /Cord>是一个典型的例子……即使在调用了<代码> STD::Prtff()时,也会出现一个典型的例子。,它仍然是原来的C
printf()
“这是用于MSVC的
名称空间本身没有名称损坏,但名称空间的名称在名称损坏时会合并到函数(或对象)的名称中。此过程未记录,但已描述
通过跳转回答您的具体问题:
1) 没有关于名称损坏的标准定义行为。标准实际上说的是,实现为extern“C”
构造提供了一个与C兼容的链接:
7.5.3[联动装置规范]
每项实施应规定:
链接到用C语言编写的函数
编程语言“C”和链接
对于C++函数,“C++”。[示例:
-[结束示例]
这最终意味着,由于C没有名称空间
s的概念,如果extern“C”
名称空间中的函数或对象,则导出的名称将失去名称空间限定。这导致
3) 是的,您可能有链接问题。试试这个:
main.h
main.cpp
谢谢,我很高兴这些陷阱相对简单,而且通常是常识性的——也许我会在构成c-ABI接口的函数上使用c风格的前缀。
complex sqrt(complex); // C + + linkage by default
extern "C" { double sqrt(double); // C linkage }
#ifndef MAIN_API
# define MAIN_API __declspec(dllexport)
#endif
namespace x
{
extern "C" MAIN_API void foo();
};
namespace y
{
extern "C" MAIN_API void foo();
};
#include <cstdlib>
#include <iostream>
using namespace std;
#define MAIN_API __declspec(dllexport)
#include "main.h"
void x::foo()
{
cout << "x::foo()\n";
}
void y::foo()
{
cout << "y::foo()\n";
}
int main()
{
}
#ifndef MAIN_API
# define MAIN_API __declspec(dllexport)
#endif
namespace x
{
extern "C" MAIN_API void x_foo();
};
namespace y
{
extern "C" MAIN_API void y_foo();
};