前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >在 C++ 中命名 Mangling 和 extern “C”

在 C++ 中命名 Mangling 和 extern “C”

作者头像
鲸落c
发布2022-11-14 16:44:10
1.1K0
发布2022-11-14 16:44:10
举报
文章被收录于专栏:鲸落学习笔记鲸落学习笔记

theme: channing-cyan highlight: a11y-dark


「这是我参与11月更文挑战的第20天,活动详情查看:2021最后一次更文挑战

C++ 支持函数重载,即可以有多个同名但不同参数的函数。C++ 编译器在生成目标代码时如何区分不同的函数——它通过添加有关参数的信息来更改名称。这种向函数名称添加附加信息的技术称为Name Mangling。C++ 标准没有指定任何特定的名称修改技术,因此不同的编译器可能会向函数名称附加不同的信息。 

考虑以下 Name Mangling 示例,其中包含函数f() 的各种声明

代码语言:javascript
复制
int f(void) { return 1; }
int f(int) { return 0; }
void g(void) { int i = f(), j = f(0); }

一些 C++ 编译器可能会将上述名称改写为以下名称,

代码语言:javascript
复制
int __f_v(void) { return 1; }
int __f_i(int) { return 0; }
void __g_v(void) { int i = __f_v(), j = __f_i(0); }

注意:  C 不支持函数重载,因此,当我们在 C++ 中链接 C 代码时,我们必须确保符号的名称不被更改。

从 C++ 链接时如何处理 C 符号?

在 C 中,名称可能不会被修改,因为它不支持函数重载。那么当我们在 C++ 中链接 C 代码时,如何确保符号的名称不被更改。例如,请参阅以下使用 C 的 printf() 函数的 C++ 程序。 

代码语言:javascript
复制
#include <stdio.h>
int printf(const char* format, ...);

int main()
{
    printf("haiyong");
    return 0;
}

上述程序产生错误。

解释: 编译错误的原因很简单,c++编译器修改了printf() 的名字,没有找到新名字的函数定义。

解决方案:  C++ 中的 Extern “C”

当一些代码被放入 extern “C” 块时,C++ 编译器确保函数名是未修改的——编译器发出一个名称不变的二进制文件,就像 C 编译器会做的那样。

如果我们把上面的程序改成下面这样,程序就可以正常工作并在控制台上打印“haiyong”(如下所示)。

代码语言:javascript
复制
#include <bits/stdc++.h>
using namespace std;

extern "C" {
int printf(const char* format, ...);
}

int main()
{
    printf("haiyong");
    return 0;
}

输出

代码语言:javascript
复制
haiyong

因此,所有 C 风格的头文件(stdio.h、string.h 等)在 extern “C”块中都有它们的声明。

代码语言:javascript
复制
#ifdef __cplusplus
extern "C" {
#endif
// Declarations of this file
#ifdef __cplusplus
}
#endif

以下是上面讨论的要点:

1. 由于 C++ 支持函数重载,因此必须在函数名称中添加附加信息(称为 Name mangling)以避免二进制代码中的冲突。  2.  C 中不能更改函数名称,因为它不支持函数重载。为了避免链接问题,C++ 支持 extern “C” 块。C++ 编译器确保 extern “C” 块内的名称不会更改。

如果您发现任何不正确的内容,或者您​​想分享有关上述主题的更多信息,请发表评论。

本文参与 腾讯云自媒体分享计划,分享自作者个人站点/博客。
原始发表:2021-11-29,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体分享计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • 从 C++ 链接时如何处理 C 符号?
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档