斩获3.4k+Star的C++Insights:用编译器的视角看源码!

C语言与CPP编程 2024-05-16 09:00

本文经授权转自公众号CSDN(ID:CSDNnews)

作者 | Andreas Fertig
翻译 | 郑丽媛

近日在新闻平台 HackerNews 上有个开发者颇为关注的 GitHub 项目,名叫 C++ Insights,特色就是:用编译器的眼睛看源码。为此,项目作者对其进行了详细介绍。

文链接:https://github.com/andreasfertig/cppinsights


1、C++ Insights 是什么?

C++ Insights 是一种基于 Clang 的工具,可进行源码到源码的转换,其目标是揭示通常情况下编译器在幕后为我们做的工作。它能帮我们看到编译器为了让代码正常运行而进行的一些神奇操作。

以下面这段代码为例:

class Base {};
class Derived : public Base {};
int main() { Derived d;
Derived d2 = d;
d2 = d;
Base& b = d;}

没有什么特别之处,当然也能编译。下面是编译器对它的看法:

class Base{  public:  // inline constexpr Base() noexcept = default;  // inline constexpr Base(const Base &) noexcept = default;  // inline constexpr Base & operator=(const Base &) noexcept = default;};


class Derived : public Base{ public: // inline constexpr Derived() noexcept = default; // inline constexpr Derived(const Derived &) noexcept = default; // inline constexpr Derived & operator=(const Derived &) noexcept = default;};
int main(){ Derived d; Derived d2 = Derived(d); d2.operator=(d); Base & b = static_cast(d); return 0;}

你可以看到所有由编译器提供的特殊成员函数,以及从 Derived 向 Base 的向上转型。

2、为什么要做 C++ Insights?

2017 年,我开始研究 C++11、C++14 和 C++17 带来的一些新特性,如 lambda 表达式、基于范围的 for 循环和结构化绑定等。然而,所有这些研究以及我的一些培训和教学经历让我开始思考:如果我们能以编译器的视角来洞悉代码,那将会是怎样一番景象?当然,至少对于 Clang 来说,是有 AST(抽象语法树)转储功能的,我们可以用 Compiler Explorer 等工具查看编译器从 C++ 源代码片段生成的代码。不过,我们看到的是汇编程序,AST 和 Compiler Explorer 的输出并不是我写代码的语言,因此我对这些输出并不熟悉。另外,在教学生 C++ 时,如果跟他们展示 AST 并解释说这就是全部内容,我自己感觉也不太满意。

于是,我开始着手编写一个基于 Clang 的工具,可将基于范围的 for 循环转换为编译器内部版本。接着,我对结构化绑定和 lambda 也做了同样的处理。最终,我的工作超出了最初计划。 

C++ Insights 这个工具显示了运算符的调用位置,以及编译器进行类型转换的情况,可以推断出 auto 或 decltype 背后的类型。我的目标是生成可编译的代码,然而,并非所有情况都能实现这一点。

例如,你可以看到 lambda、基于范围的 for 循环或 auto 的转换。当然,你也可以转换任何其他 C++ 代码段。

感兴趣的话,你可以亲自试试看。C++ Insights 在线使用网址:https://cppinsights.io/

不过,还有很多工作要做。我不敢说我做的一切都是正确的,目前我还在努力支持 C++20 等新标准的特性。请记住,C++ Insights 是基于 Clang 及其对 AST 的理解而建立的。

3、如何构建?

C++ Insights 可以在 Clang 源代码树内部或外部进行构建。

(1)在 Windows 上构建

已测试(支持的编译器)

注意:仅支持在 LLVM 外部构建。不支持 x86,因为没有针对 x86 的 LLVM/Clang 库。

对于带有 VS 的 Clang:

  • 前往 LLVM 下载页面;

  • 从“Pre-Built Binaries”部分安装“Windows(64位)”;

安装程序会自动将 LLVM 工具集添加到你所有 Visual Studio 实例中。

从源代码构建和安装 Clang

需要有 Clang 库和 llvm-config.exe 来设置 CMake。

将 Clang/LLVM 库安装到(例如)C:\Programs\LLVM_local2。

注意:

  • 安装路径中不能有空格;

  • 最好不要使用 %Program Files%,否则需要管理员权限来安装文件。

git clone https://github.com/llvm/llvm-project.gitcd llvm-projectmkdir buildcd buildcmake -DLLVM_ENABLE_PROJECTS=clang ^      -DCMAKE_INSTALL_PREFIX=C:\Programs\LLVM_local2 ^      -G "Visual Studio 15 2017" ^      -A x64 ^      -Thost=x64 ^      ..\llvmcmake --build . --config Release --target install

你也可以在 Visual Studio 中打开 build/LLVM.sln 解决方案,然后在其中构建所有内容,而不是使用 cmake --build ... 命令。

构建 Insights 

假设:

  • C++ Insights 源代码位于 C:\dev\cppinsights,并且

  • LLVM/Clang 已经构建并安装到 C:\Programs\LLVM_local2(参见上面的步骤)

cd C:\dev\cppinsights\mkdir buildcd buildset path=%path%;C:\Programs\LLVM_local2\bincmake -G "Visual Studio 16 2019" -A x64 -T LLVM_v142 ..cmake --build . --config Release --target insights

除了带“Visual Studio 16 2019”的 Clang,你还可以选择其他适合你的。具体可参见上面的 “已测试(支持的编译器)”,查看 CMake 命令列。另外,你也可以直接在 Visual Studio 中打开 build/cpp-insights.sln 文件进行构建,而不必通过命令行。

(2)在 Arch Linux 上构建

要使用 extra/clang 构建,请使用以下额外标记:

-DINSIGHTS_USE_SYSTEM_INCLUDES=off -DCLANG_LINK_CLANG_DYLIB=on -DLLVM_LINK_LLVM_DYLIB=on

extra/clang 和 extra/llvm 提供 /usr/lib/{libclangAST.so,libLLVM*.a,libLLVM.so},libclangAST.so 需要 libLLVM.so,如果链接的是 libLLVM*.a(而不是 libLLVM.so),就会发生冲突。

(3)在 Clang 外部构建

你需要在搜索路径中安装 Clang。

git clone https://github.com/andreasfertig/cppinsights.gitmkdir build && cd buildcmake -G"Ninja" ../cppinsightsninja

生成的二进制文件(insights)可以在 build 文件夹中找到。

(4)在 Clang 内部构建

在 Clang 源代码树中 C++ Insights 最简单的方法,是使用 LLVM_EXTERNAL_PROJECTS 选项。

git clone https://github.com/llvm/llvm-project.gitgit clone https://github.com/andreasfertig/cppinsights.git
mkdir buildcd buildcmake -G Ninja -D=CMAKE_BUILD_TYPE=Release -DLLVM_EXTERNAL_PROJECTS=cppinsights -DLLVM_EXTERNAL_CPPINSIGHTS_SOURCE_DIR= [INSIGHTS CMAKE OPTIONS] ../llvm-project/llvm
ninja

cmake 选项

cmake 可启用几个选项:

在 macOS 上构建 ARM

似乎最好在配置时提供架构:

cmake -DCMAKE_OSX_ARCHITECTURES=arm64 ../cppinsights

4、使用方法

使用 C++ Insights 非常简单:

insights  -- -std=c++17

当涉及到系统包含路径时,情况就变得复杂了。这些路径是二进制文件中的硬编码,似乎来自 C++ Insights 的编译器。要解决这个问题,可查看 scripts/getinclude.py,这个脚本会尝试从编译器中收集系统包含路径。如果没有选项,getinclude.py 将默认使用 g++,你也可以将其他编译器作为第一个参数传递。

下面是一个例子:

./scripts/getinclude.py-isystem/Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/bin/../include/c++/v1 -isystem/usr/local/include -isystem/Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/bin/../lib/clang/7.3.0/include -isystem/Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/include -isystem/usr/include

该脚本可与 C++ Insights 一起使用:

insights  -- -std=c++17 `./scripts/getinclude.py`

自定义 GCC 安装

如果你用的是自定义版本的 GCC 编译器,例如 gcc-11.2.0,且未安装在编译器的默认系统路径中,那么在构建后,Clang 将无法找到正确的 libstdc++ 路径(即 GCC 的标准模板库)。如果遇到这种情况,你可以用“--gcc-toolchain=/path/GCC-1x.x.x/installed/path”来告诉 Clang/C++ Insights STL 的位置:

./cppinsights Insights.cpp -- --gcc-toolchain=${GCC_11_2_0_INSTALL_PATH} -std=c++20

这里的“${GCC_11_2_0_INSTALL

_PATH}”是你定制构建的 GCC 安装目录。

随时可用的 Docker 容器

GitHub 上还有另一个项目,可以在其中设置一个装有最新 C++ Insights 版本的 docker 容

器:C++ Insights - Docker(https://github.com/andreasfertig/cppinsights-docker)

C++ Insights @ Vim

Vim 插件可在此处下载:https://github.c

om/Freed-Wu/cppinsights.vim

C++ Insights @ VSCode

Visual Studio Code 的扩展可在此处找到:https://marketplace.visualstudio.com/items?itemName=devtbi.vscode-cppinsights

C++ Insights @ brew

至少在 macOS 上,你可通过 Homebrew 安装 C++ Insights,这要归功于这个公式:

brew install cppinsights


5、兼容性

我的目标是,能够与最新版本的 Clang 或者至少前一个版本保持兼容,在线网站尽量与 Clang 的最新版本保持一致。然而,由于某些问题(比如为 Windows 构建 Clang),网站的版本经常会延迟几个月。

更多详细介绍,可参看 C++ Insights 项目 GitHub 地址:https://github.com/andreasfertig/cppinsights

本文转自公众号“CSDN”,ID:CSDNnews

---END---

你好,我是飞宇,本硕均于某中流985 CS就读,先后于百度搜索字节跳动电商以及携程等部门担任Linux C/C++后端研发工程师。

最近跟朋友一起开发了一个新的网站:编程资源网,已经收录了不少资源(附赠下载地址),如果屏幕前的靓仔/女想要学习编程找不到合适资源的话,不妨来我们的网站看看,欢迎扫码下方二维码白嫖~

同时,我也是知乎博主@韩飞宇,日常分享C/C++、计算机学习经验、工作体会,欢迎点击此处查看我以前的学习笔记&经验&分享的资源。

我组建了一些社群一起交流,群里有大牛也有小白,如果你有意可以一起进群交流。

欢迎你添加我的微信,我拉你进技术交流群。此外,我也会经常在微信上分享一些计算机学习经验以及工作体验,还有一些内推机会

加个微信,打开另一扇窗

C语言与CPP编程 C语言/C++开发,C语言/C++基础知识,C语言/C++学习路线,C语言/C++进阶,数据结构;算法;python;计算机基础等
评论
  • 电竞鼠标应用环境与客户需求电竞行业近年来发展迅速,「鼠标延迟」已成为决定游戏体验与比赛结果的关键因素。从技术角度来看,传统鼠标的延迟大约为20毫秒,入门级电竞鼠标通常为5毫秒,而高阶电竞鼠标的延迟可降低至仅2毫秒。这些差异看似微小,但在竞技激烈的游戏中,尤其在对反应和速度要求极高的场景中,每一毫秒的优化都可能带来致胜的优势。电竞比赛的普及促使玩家更加渴望降低鼠标延迟以提升竞技表现。他们希望通过精确的测试,了解不同操作系统与设定对延迟的具体影响,并寻求最佳配置方案来获得竞技优势。这样的需求推动市场
    百佳泰测试实验室 2025-01-16 15:45 295浏览
  • 随着智慧科技的快速发展,智能显示器的生态圈应用变得越来越丰富多元,智能显示器不仅仅是传统的显示设备,透过结合人工智能(AI)和语音助理,它还可以成为家庭、办公室和商业环境中的核心互动接口。提供多元且个性化的服务,如智能家居控制、影音串流拨放、实时信息显示等,极大提升了使用体验。此外,智能家居系统的整合能力也不容小觑,透过智能装置之间的无缝连接,形成了强大的多元应用生态圈。企业也利用智能显示器进行会议展示和多方远程合作,大大提高效率和互动性。Smart Display Ecosystem示意图,作
    百佳泰测试实验室 2025-01-16 15:37 194浏览
  • 百佳泰特为您整理2025年1月各大Logo的最新规格信息,本月有更新信息的logo有HDMI、Wi-Fi、Bluetooth、DisplayHDR、ClearMR、Intel EVO。HDMI®▶ 2025年1月6日,HDMI Forum, Inc. 宣布即将发布HDMI规范2.2版本。新规范将支持更高的分辨率和刷新率,并提供更多高质量选项。更快的96Gbps 带宽可满足数据密集型沉浸式和虚拟应用对传输的要求,如 AR/VR/MR、空间现实和光场显示,以及各种商业应用,如大型数字标牌、医疗成像和
    百佳泰测试实验室 2025-01-16 15:41 189浏览
  • 随着消费者对汽车驾乘体验的要求不断攀升,汽车照明系统作为确保道路安全、提升驾驶体验以及实现车辆与环境交互的重要组成,日益受到业界的高度重视。近日,2024 DVN(上海)国际汽车照明研讨会圆满落幕。作为照明与传感创新的全球领导者,艾迈斯欧司朗受邀参与主题演讲,并现场展示了其多项前沿技术。本届研讨会汇聚来自全球各地400余名汽车、照明、光源及Tier 2供应商的专业人士及专家共聚一堂。在研讨会第一环节中,艾迈斯欧司朗系统解决方案工程副总裁 Joachim Reill以深厚的专业素养,主持该环节多位
    艾迈斯欧司朗 2025-01-16 20:51 144浏览
  •  光伏及击穿,都可视之为 复合的逆过程,但是,复合、光伏与击穿,不单是进程的方向相反,偏置状态也不一样,复合的工况,是正偏,光伏是零偏,击穿与漂移则是反偏,光伏的能源是外来的,而击穿消耗的是结区自身和电源的能量,漂移的载流子是 客席载流子,须借外延层才能引入,客席载流子 不受反偏PN结的空乏区阻碍,能漂不能漂,只取决于反偏PN结是否处于外延层的「射程」范围,而穿通的成因,则是因耗尽层的过度扩张,致使跟 端子、外延层或其他空乏区 碰触,当耗尽层融通,耐压 (反向阻断能力) 即告彻底丧失,
    MrCU204 2025-01-17 11:30 146浏览
  • 日前,商务部等部门办公厅印发《手机、平板、智能手表(手环)购新补贴实施方案》明确,个人消费者购买手机、平板、智能手表(手环)3类数码产品(单件销售价格不超过6000元),可享受购新补贴。每人每类可补贴1件,每件补贴比例为减去生产、流通环节及移动运营商所有优惠后最终销售价格的15%,每件最高不超过500元。目前,京东已经做好了承接手机、平板等数码产品国补优惠的落地准备工作,未来随着各省市关于手机、平板等品类的国补开启,京东将第一时间率先上线,满足消费者的换新升级需求。为保障国补的真实有效发放,基于
    华尔街科技眼 2025-01-17 10:44 202浏览
  • 现在为止,我们已经完成了Purple Pi OH主板的串口调试和部分配件的连接,接下来,让我们趁热打铁,完成剩余配件的连接!注:配件连接前请断开主板所有供电,避免敏感电路损坏!1.1 耳机接口主板有一路OTMP 标准四节耳机座J6,具备进行音频输出及录音功能,接入耳机后声音将优先从耳机输出,如下图所示:1.21.2 相机接口MIPI CSI 接口如上图所示,支持OV5648 和OV8858 摄像头模组。接入摄像头模组后,使用系统相机软件打开相机拍照和录像,如下图所示:1.3 以太网接口主板有一路
    Industio_触觉智能 2025-01-20 11:04 111浏览
  • Ubuntu20.04默认情况下为root账号自动登录,本文介绍如何取消root账号自动登录,改为通过输入账号密码登录,使用触觉智能EVB3568鸿蒙开发板演示,搭载瑞芯微RK3568,四核A55处理器,主频2.0Ghz,1T算力NPU;支持OpenHarmony5.0及Linux、Android等操作系统,接口丰富,开发评估快人一步!添加新账号1、使用adduser命令来添加新用户,用户名以industio为例,系统会提示设置密码以及其他信息,您可以根据需要填写或跳过,命令如下:root@id
    Industio_触觉智能 2025-01-17 14:14 78浏览
  • 本文介绍瑞芯微开发板/主板Android配置APK默认开启性能模式方法,开启性能模式后,APK的CPU使用优先级会有所提高。触觉智能RK3562开发板演示,搭载4核A53处理器,主频高达2.0GHz;内置独立1Tops算力NPU,可应用于物联网网关、平板电脑、智能家居、教育电子、工业显示与控制等行业。源码修改修改源码根目录下文件device/rockchip/rk3562/package_performance.xml并添加以下内容,注意"+"号为添加内容,"com.tencent.mm"为AP
    Industio_触觉智能 2025-01-17 14:09 115浏览
  • 80,000人到访的国际大展上,艾迈斯欧司朗有哪些亮点?感未来,光无限。近日,在慕尼黑electronica 2024现场,ams OSRAM通过多款创新DEMO展示,以及数场前瞻洞察分享,全面展示自身融合传感器、发射器及集成电路技术,精准捕捉并呈现环境信息的卓越能力。同时,ams OSRAM通过展会期间与客户、用户等行业人士,以及媒体朋友的深度交流,向业界传达其以光电技术为笔、以创新为墨,书写智能未来的深度思考。electronica 2024electronica 2024构建了一个高度国际
    艾迈斯欧司朗 2025-01-16 20:45 183浏览
  • 2024年是很平淡的一年,能保住饭碗就是万幸了,公司业绩不好,跳槽又不敢跳,还有一个原因就是老板对我们这些员工还是很好的,碍于人情也不能在公司困难时去雪上加霜。在工作其间遇到的大问题没有,小问题还是有不少,这里就举一两个来说一下。第一个就是,先看下下面的这个封装,你能猜出它的引脚间距是多少吗?这种排线座比较常规的是0.6mm间距(即排线是0.3mm间距)的,而这个规格也是我们用得最多的,所以我们按惯性思维来看的话,就会认为这个座子就是0.6mm间距的,这样往往就不会去细看规格书了,所以这次的运气
    wuliangu 2025-01-21 00:15 49浏览
我要评论
0
点击右上角,分享到朋友圈 我知道啦
请使用浏览器分享功能 我知道啦