基于Vscode搭建Windows平台基于WSL2的Ascend C算子开发和调试集成开发环境,提升Ascend C算子开发和调试效率。
1 概述
本文简要介绍什么是Vscode, 为什么要使用Vscode,以及如何使用Vscode进行Ascend c算子开发和调试。
2 Vscode介绍
Visual Studio Code 是一款流行的编辑器, 以易用性、可扩展性、速度和灵活性为关键特征。
Vscode和Gvim相比,具有更丰富的插件和图形化操作命令,例如Vscode结合CMake tools、gdb等,可以配置为一个简易的IDE,支持断点调试,提升开发效率。Vscode中安装vim插件后,也支持vim风格的代码编辑,从而结合两者的优势,提升开发效率。
Vscode和Visual studio相比,前者主要是编辑器,后者是专业的IDE。前者可以通过丰富的插件,配置后支持不同的编程语言开发;后者直接支持多种开发任务,包括测试,但是不能很好支持Linux环境的开发。可以这样说,Vscode是Visual studio的编辑器开发界面体验的剥离,借鉴了Vim/IntelliJ等丰富插件系统思想的结合,突出了编辑能力和灵活配置能力。
3 Vscode应知应会
在Windows中安装好Vscode后,打开Vscode可以看到主界面,可以通过介绍的视频起步,对Vscode的特性快速获得一个整体的了解:
-
-
-
-
-
-
Introductory Videos (Overall)
https://code.visualstudio.com/docs/getstarted/introvideos#Vscode
-
-
-
-
-
-
Getting Starged
https://code.visualstudio.com/docs/introvideos/basics
-
-
-
-
-
-
Code Editing
https://code.visualstudio.com/docs/introvideos/codeediting
-
-
-
-
-
-
Productivity Tips
https://code.visualstudio.com/docs/introvideos/productivity
-
-
-
-
-
-
Personalize
https://code.visualstudio.com/docs/introvideos/configure
-
-
-
-
-
-
Extensions
https://code.visualstudio.com/docs/introvideos/extend
-
-
-
-
-
-
Debugging
https://code.visualstudio.com/docs/introvideos/debugging
-
-
-
-
-
-
Version Control
https://code.visualstudio.com/docs/introvideos/versioncontrol
-
-
-
-
-
-
Customize
https://code.visualstudio.com/docs/introvideos/customize
对于Linux环境开发的用户,可以通过WSL2安装Linux系统后,从Linux的Shell中启动Vscode,获得一致的开发体验。
3.2 界面
主界面左侧的Primary Side Bar中从上之下,包含了主要的工作区浏览器、搜索、版本管理、运行和调试、扩展等功能。
-
-
-
-
-
-
a) Explorer
该功能区将展示打开的编辑器、打开的文件夹、Outline和Timeline等信息。其中Outline将显示每个文本编辑器中内容的概览,例如C语言代码的宏定义、函数、类等,Timeline将显示版本管理历史,从空间和时间两个维度查看被编辑文件。
-
-
-
-
-
-
b) Search
搜索功能支持大小写、整个词语、以及正则表达式等多种搜索方式,从目录文件中检索内容,还包括对内容进行替换。这个功能对应grep和sed的图形化界面操作版,这个功能绝对是编程开发的利器之一。
-
-
-
-
-
-
c) Source Control
支持通过GIT对目录内容进行版本管理,包括GIT的常用操作,通通都是图形化界面的操作方式,相对更加方便实用。
-
-
-
-
-
-
d) Run and Debug
这是编程开发的运行和调试界面,包括Debug Console、Variables、Watch、Call Stack、Breakpoints等几个显示界面。其中Debug Console中还包括输入文本栏,可以动态地输入可执行的debug表达式,例如gdb设置指令。
-
-
-
-
-
-
e) Extenstions
在线的插件市场,可以查找并安装需要的各种插件,对Vscode的能力进行扩展。
3.3 基本编辑
可以使用Vscode提供的快捷键实现诸如多cursor选择和编辑、行移动等高级编辑功能,参考Code Editing(https://code.visualstudio.com/docs/introvideos/codeediting )。
另外可以安装Vim插件(Vscodevim),利用vim提供的编辑风格,进行高效率的文本编辑。
常用快捷键:
Ctrl+Shift+P:Command Pallette,所有命令的入口。
Ctrl+G:Terminal中,回到之前的目录。
Ctrl+R:搜索之前的命令。
Ctrl+Shift+E: Expoler
Ctrl+Shift+F: Search/Find
Ctrl+Shift+G: Git
Ctrl+Shift+D: Debug/Run
Ctrl+Shift+X: Extension
Ctrl+`:打开内嵌的Shell
…
3.4 常用扩展
Vim:Vscode中模拟vim编辑器。
WSL:支持WSL系统中的文件打开,获得Vscode的所有特性支持,可以方便windows平台进行Linux环境的开发,极大提升效率。
C/C++ Themes:C/C++的主题,包括Light和Dark。
C/C++:C/C++的IntelliSense, 调试和代码浏览,不包括编译器。
CMake:Vscode中的CMake语言支持,主要包括CMakeList.txt文件语法高亮和补全。
CMakeTools:提供Vscode中基于CMake创建工程的全部特性和工作流,从而实现Windows和Linux等的跨平台项目构建。
C/C++ Extension Pack:包括C/C++, C/C++ Themes,CMake,CMakeTools四个插件的Pack。
Python:Vscode的Python语言支持插件,包括IntelliSense,Linting,debugging,code formatting,refactoring,unit test,甚至包括notebook的打开编辑和调试,以及画图等,Python虚拟环境创建和管理等,以及更多。
Pylance: Python语言的language server,包含在Python插件依赖里。
Jupyter: 支持在Vscode中编辑Jupyter笔记文件。
Makefile Tools:Makefile插件,提供C/C++ IntelliSense,构建,调试和运行等。
Live Preview:实时预览网页,以及Markdown等。
3.5 WSL2集成
在WSL的Linux系统Shell中,将Vscode的可执行文件目录添加到PATH中,例如:
export PATH=$PATH:'/mnt/c/Program Files/Microsoft Vscode/bin/'
然后在WSL目标目录中可以执行code ., 这将会在WSL系统中安装WSL VscodeServer,从而与Windows中的Vscode连接。
WSL2中进行Linux环境开发,需要安装对应的插件到WSL Vscode Server中,才可以获得对应的功能,例如Python/C/C++/CMake等插件,需要同时安装Local和Remote端,然后就可以获得对应的支持。
4 Vscode中的C/C++调试
4.1 基本流程
安装好C/C++ Pack插件后,可以创建CPP文件,并且启动运行和调试,选择一个工具链后进行调试。
4.2 一个示例
创建一个目录,并用code打开:
mkdir sample_cpp
code sample_cpp

图 2 Vscode中打开sample_cpp目录
创建main.cpp,并输入内容:

图 3 Vscode的C/C++目录中的C示例源代码
如果没有安装C/C++ Pack插件,则按照提示安装,之后可以添加调试配置(Debug Configuration):

图 4 Vscode中添加C/C++调试配置

图 5 Vscode中选择C/C++的预定义调试配置
如果是C语言可以选择gcc,如果是C++,可以选择g++,如果wsl的Linux系统中没有,则需要提前安装,例如apt install build-essential gdb等。
设置断点后,通过F5进行调试。

图 6 Vscode中对单个C/C++文件进行调试
Vscode是如何做到的呢?这是通过Debug Configuration的配置完成的。过去,在Visual Studio等IDE中,对C/C++编译的设置,有详细的图形化配置界面,可以设置编译、链接、调试等等过程配置参数,而在Vscode中,所有设置都在launch.json文件中给出。可以看到,C/C++:gcc build and debug active file的配置里,设置了目标程序、当前目录、调试程序(gdb)、启动设置命令(setupCommands)、前置任务(C/C++: gcc build active file)等信息。

图 7 Vscode的launch.json配置
在前置的Task,C/C++:gcc build active file的配置存在于tasks.json里,可以看到,这里同样有命令、参数和目标,同时我们注意到这里添加了-g选项,支持编译过程中的调试符号嵌入。

图 8 Vscode的tasks.json配置
4.3 如何拓展到复杂的C/C++工程
从上述示例,我们可以看到Vscode对简单C/C++文件的编译和调试处理方式,主要是json文件格式的tasks.json和launch.json进行配置。
复杂的C/C++工程典型的特征就是多个文件,多个模块,涉及到分别编译和相互链接,同时涉及到公共动态库的链接等,同时一个项目可能包含多个可执行目标。那么Vscode如何拓展到复杂的C/C++工程开发和调试呢?答案就是借助CMake工具,以跨平台的方式,将复杂工程的构建规则预先设置好。
5 Vscode中的CMake工程
5.1 Make简介
很多开源代码的代码树里都包含一个Makefile的文件,实际上这个文件就是从源代码到可执行代码构建过程的规则描述,可以看做是源代码都是做菜的原材料或者半成品,可以根据Makefile这个“菜单”描述的步骤,“构建”出最终的“菜品”(也就是软件)来。
Makefile的基本格式就是一系列的目标和依赖规则:
Target1:Dependency1
Build Rule1
Target2:Dependency2
Build Rule2
其中Target可以作为其它Target的Dependency,因此要构建一个目标,需要先构建其依赖。这是一个嵌套的过程,而且可以检查不同目标的构建时间戳,和其依赖的时间戳进行比较,只有依赖更改过,才能触发该目标的重新构建,这可以实现大型项目的增量构建,极大地节约时间。
Makefile的构建规则通常对应不同操作系统下不同的开发工具链的命令,为了同时适配Windows、Linux、Mac OS等不同的操作系统,以及不同的工具链(gcc, msvc, clang等),以及不同的IDE(visual studio, eclipse等),CMake应运而生。CMake工具的目标是Cross platform的Make,通过CMake的更简单理解的语言为每个目录的文件撰写CMakeList.txt文件,实现开发环境和依赖的探测,整个工程的构建,例如生成Visual Studio的工程,Makefile的工程,以及Eclipse的工程等。简单来说,CMake提取更高层和更凝练的信息,然后自动地生成makefile/工程文件等更底层的构建规则文件,并且可以实现跨平台。
5.2 CMake简介
CMake工具可以实现复杂工程跨平台的构建规则撰写。通常,在工程主目录下的CMakeList.txt包含Project的定义和依赖环境的检测,例如C/C++工程依赖的其它动态库头文件和动态库链接文件的位置,设置编译配置,编译参数等,再包含各个子目录。在子目录的CMakeList.txt文件中,包含该目录对应的模块的编译目标规则。
基于CMake描述构建规则的项目,可以实现out of source的构建,例如使用CMake的工程,构建命令通常都是:
mkdir build
CMake ..
这样可以实现所有构建过程产生的文件都位于build目录下,不影响外面的源代码树。
5.3 Vscode中的CMake工具集成
CMake和CMake Tools两个插件提供了Vscode中对CMake工程的支持,重点包括基于CMake的项目配置、构建和调试功能。
CMake Tools插件提供了相关的文档说明,值得一读。

图 9 CMake Tools文档链接
5.4 Quick Start
通过Ctrl+Shift+P,选择CMake:quick start可以基于向导,快速添加一个CMake项目,例如可执行文件目标。这会在当前目录,添加CMakeList.txt,添加必要的源文件,以及设置好工程。用户可以在此基础上进行修改。
在使用CMake构建项目之前,需要通过CMake:Select a kit,选择开发工具链,例如gcc/g++。通过CMake:Select Variant,选择项目变体,例如Debug。通过CMake:configure,触发CMake进行配置。
配置好项目后,就可以开始构建项目了,可以采用CMake: Build命令,或者状态栏中的Build按钮。默认情况下构建所有目标,也可以通过CMake: Set Build Target设置需要构建的目标。
所有的CMake状态和目标,都可以从CMake界面中显示出来(CMake: Focus on Project Status View):

图 10 Vscode中CMake插件的项目状态视图
相应的命令:Configure, Build, Test, Debug, Launch 都可以从对应的目标右侧按钮启动。

图 11 Vscode中CMake插件的不同功能按钮
5.5 CMake Tools的更多功能
5.5.1 启动参数
可以在Open User Settings (JSON)命令中,对settings.json进行修改。

图 12 Vscode中打开用户设置命令
例如添加配置阶段的参数,或者构建阶段的参数,设置不同的项目生成器等。

图 13 Vscode中的用户设置
5.5.2 查看配置和构建的命令
通过Show Build Command和Show Configure Command可以查看配置和构建的命令,方便排查问题。

图 14 Vscode中CMake显示构建命令
5.5.3 排查CMake配置问题
可以使用message(STATUS ${target_variables}),打印内部变量的值,方便排查问题。
6 Vscode中的Ascend C算子工程调试
Ascend C算子开发的Hello world工程就是两个张量的加法算子,位于samples/cplusplus/level1_single_api/4_op_dev/6_ascendc_custom_op/kernel_invocation/Add目录下。

图 15 Ascend C自定义算子开发Add算子示例工程
该项目是一个CMake工程,并且提供了run.sh脚本作为项目构建的统一入口(在其中调用CMake构建和运行)。
如果我们希望参考该工程,开发自己的算子,并用Vscode对算子工程进行调试的话,可以利用Vscode基于gdb提供的调试能力,辅助我们快速地调试自定义算子的精度。
6.1 打开Vscode前的准备工作
-
-
-
-
-
-
1 如FAQ所述,如果不希望root用户运行Vscode,需要配置/etc/wsl.conf
2 为了让Ascend C算子能够正确地链接,需要source /usr/local/Ascend/ascend-toolkit/latest/bin/setenv.bash,提前设置好LD_LIBRARY_PATH。
需要注意的是Vscode安装路径通常包含空格,例如export PATH=$PATH:'/mnt/c/Program Files/Microsoft Vscode/bin/',在上面第二步之后,PATH环境变量中的空格后面的部分可能会丢掉,因此需要再次添加Vscode的路径到PATH中。
6.2 打开Vscode进行配置、构建和调试
-
-
-
-
-
-
1 配置
通过Open User Settings (JSON)命令,打开settings.json。

图 16 Vscode中打开用户设置命令
设置CMake配置参数,例如smoke_testcase、ASCEND_PRODUCT_TYPE、ASCEND_CORE_TYPE、ASCEND_RUN_MODE、ASCEND_INSTALL_PATH、generator等。

图 17 Vscode中用户设置AscendC算子工程参数
选择工具链,Select a kit.

图 18 Vscode中选择C/C++工具链
(可选)查看配置命令:Show Configure Command。

图 19 Vscode中查看CMake的配置命令
配置,CMake:configure。

图 20 Vscode中执行CMake的配置
-
-
-
-
-
-
2 构建
通过CMake: set build target命令,设置构建目标为add_custom_cpu。

图 21 Vscode中设置CMake构建目标
(可选)查看构建命令,CMake:show build command。

图 22 Vscode中查看CMake构建命令
通过CMake: buid,构建目标,或者点击camke status view中的build按钮。

图 23 Vscode中CMake成功构建目标
-
-
-
-
-
-
3 调试
设置断点,注意一定要在ICPU_RUN_KF宏位置设置断点,以及在算子类中设置断点。

图 24 调用核函数前的断点

图 25 算子类方法的断点
调用Python脚本,生成激励数据和真值数据。
python3 add_custom.py
通过CMake: set debug target设置调试目标为add_custom_cpu。
通过CMake: debug命令,开始调试,代码将停在ICPU_RUN_KF位置:

图 26 Vscode中调试时断点停在核函数调用前
在Debug Console中,输入:
-exec set follow-fork-mode child

图 27 Vscode中在调试终端设置和显示不同的gdb选项
然后Continue,程序将进入算子类的第一个单核调用中。

图 28 Vscode中进入算子类调试算子多核实现
gdb调试多进程,有一系列的选项可以进行设置,可以通过show和set进行查看和修改设置。调试多进程的常用设置包括follow-fork-mode child/parent, detach-on-fork on/off, schedule-multiple on/off,用info inferiors 查看进程列表,用attach pid可以绑定进程,设置follow-fork-mode child和detach-on-fork on 可以调试其中的算子进程,同时其它进程挂起,如果需要其它进程继续执行,可以设置schedule-multiple on。

图 29 Vscode中调试Ascend C算子时显示进程列表
7 FAQ
7.1 WSL中启动Vscode,无论是哪个用户启动,得到的都是root用户权限的Vscode和root权限的Terminal?
这是因为Vscode的用户继承自第一个Shell的用户,默认启动wsl是通过root运行的,因此无论su到哪个用户,最终启动Vscode后,都将获得root用户权限。
如果希望改变这一点,可以通过修改/etc/wsl.conf,修改默认用户:

图 30 WSL的示例配置
然后通过wsl.exe --shutdown,关闭wsl后重启,可以指定用户执行Vscode。
基于Vscode搭建Windows平台基于WSL2的Ascend C算子开发和调试集成开发环境,提升Ascend C算子开发和调试效率。
1 概述
本文简要介绍什么是Vscode, 为什么要使用Vscode,以及如何使用Vscode进行Ascend c算子开发和调试。
2 Vscode介绍
Visual Studio Code 是一款流行的编辑器, 以易用性、可扩展性、速度和灵活性为关键特征。
Vscode和Gvim相比,具有更丰富的插件和图形化操作命令,例如Vscode结合CMake tools、gdb等,可以配置为一个简易的IDE,支持断点调试,提升开发效率。Vscode中安装vim插件后,也支持vim风格的代码编辑,从而结合两者的优势,提升开发效率。
Vscode和Visual studio相比,前者主要是编辑器,后者是专业的IDE。前者可以通过丰富的插件,配置后支持不同的编程语言开发;后者直接支持多种开发任务,包括测试,但是不能很好支持Linux环境的开发。可以这样说,Vscode是Visual studio的编辑器开发界面体验的剥离,借鉴了Vim/IntelliJ等丰富插件系统思想的结合,突出了编辑能力和灵活配置能力。
3 Vscode应知应会
在Windows中安装好Vscode后,打开Vscode可以看到主界面,可以通过介绍的视频起步,对Vscode的特性快速获得一个整体的了解:
Introductory Videos (Overall)
https://code.visualstudio.com/docs/getstarted/introvideos#Vscode
Getting Starged
https://code.visualstudio.com/docs/introvideos/basics
Code Editing
https://code.visualstudio.com/docs/introvideos/codeediting
Productivity Tips
https://code.visualstudio.com/docs/introvideos/productivity
Personalize
https://code.visualstudio.com/docs/introvideos/configure
Extensions
https://code.visualstudio.com/docs/introvideos/extend
Debugging
https://code.visualstudio.com/docs/introvideos/debugging
Version Control
https://code.visualstudio.com/docs/introvideos/versioncontrol
Customize
https://code.visualstudio.com/docs/introvideos/customize
对于Linux环境开发的用户,可以通过WSL2安装Linux系统后,从Linux的Shell中启动Vscode,获得一致的开发体验。
3.2 界面
主界面左侧的Primary Side Bar中从上之下,包含了主要的工作区浏览器、搜索、版本管理、运行和调试、扩展等功能。
a) Explorer
该功能区将展示打开的编辑器、打开的文件夹、Outline和Timeline等信息。其中Outline将显示每个文本编辑器中内容的概览,例如C语言代码的宏定义、函数、类等,Timeline将显示版本管理历史,从空间和时间两个维度查看被编辑文件。
b) Search
搜索功能支持大小写、整个词语、以及正则表达式等多种搜索方式,从目录文件中检索内容,还包括对内容进行替换。这个功能对应grep和sed的图形化界面操作版,这个功能绝对是编程开发的利器之一。
c) Source Control
支持通过GIT对目录内容进行版本管理,包括GIT的常用操作,通通都是图形化界面的操作方式,相对更加方便实用。
d) Run and Debug
这是编程开发的运行和调试界面,包括Debug Console、Variables、Watch、Call Stack、Breakpoints等几个显示界面。其中Debug Console中还包括输入文本栏,可以动态地输入可执行的debug表达式,例如gdb设置指令。
e) Extenstions
在线的插件市场,可以查找并安装需要的各种插件,对Vscode的能力进行扩展。
3.3 基本编辑
可以使用Vscode提供的快捷键实现诸如多cursor选择和编辑、行移动等高级编辑功能,参考Code Editing(https://code.visualstudio.com/docs/introvideos/codeediting )。
另外可以安装Vim插件(Vscodevim),利用vim提供的编辑风格,进行高效率的文本编辑。
常用快捷键:
Ctrl+Shift+P:Command Pallette,所有命令的入口。
Ctrl+G:Terminal中,回到之前的目录。
Ctrl+R:搜索之前的命令。
Ctrl+Shift+E: Expoler
Ctrl+Shift+F: Search/Find
Ctrl+Shift+G: Git
Ctrl+Shift+D: Debug/Run
Ctrl+Shift+X: Extension
Ctrl+`:打开内嵌的Shell
…
3.4 常用扩展
Vim:Vscode中模拟vim编辑器。
WSL:支持WSL系统中的文件打开,获得Vscode的所有特性支持,可以方便windows平台进行Linux环境的开发,极大提升效率。
C/C++ Themes:C/C++的主题,包括Light和Dark。
C/C++:C/C++的IntelliSense, 调试和代码浏览,不包括编译器。
CMake:Vscode中的CMake语言支持,主要包括CMakeList.txt文件语法高亮和补全。
CMakeTools:提供Vscode中基于CMake创建工程的全部特性和工作流,从而实现Windows和Linux等的跨平台项目构建。
C/C++ Extension Pack:包括C/C++, C/C++ Themes,CMake,CMakeTools四个插件的Pack。
Python:Vscode的Python语言支持插件,包括IntelliSense,Linting,debugging,code formatting,refactoring,unit test,甚至包括notebook的打开编辑和调试,以及画图等,Python虚拟环境创建和管理等,以及更多。
Pylance: Python语言的language server,包含在Python插件依赖里。
Jupyter: 支持在Vscode中编辑Jupyter笔记文件。
Makefile Tools:Makefile插件,提供C/C++ IntelliSense,构建,调试和运行等。
Live Preview:实时预览网页,以及Markdown等。
3.5 WSL2集成
在WSL的Linux系统Shell中,将Vscode的可执行文件目录添加到PATH中,例如:
export PATH=$PATH:'/mnt/c/Program Files/Microsoft Vscode/bin/'
然后在WSL目标目录中可以执行code ., 这将会在WSL系统中安装WSL VscodeServer,从而与Windows中的Vscode连接。
WSL2中进行Linux环境开发,需要安装对应的插件到WSL Vscode Server中,才可以获得对应的功能,例如Python/C/C++/CMake等插件,需要同时安装Local和Remote端,然后就可以获得对应的支持。
4 Vscode中的C/C++调试
4.1 基本流程
安装好C/C++ Pack插件后,可以创建CPP文件,并且启动运行和调试,选择一个工具链后进行调试。
4.2 一个示例
创建一个目录,并用code打开:
mkdir sample_cpp
code sample_cpp
图 2 Vscode中打开sample_cpp目录
创建main.cpp,并输入内容:
图 3 Vscode的C/C++目录中的C示例源代码
如果没有安装C/C++ Pack插件,则按照提示安装,之后可以添加调试配置(Debug Configuration):
图 4 Vscode中添加C/C++调试配置
图 5 Vscode中选择C/C++的预定义调试配置
如果是C语言可以选择gcc,如果是C++,可以选择g++,如果wsl的Linux系统中没有,则需要提前安装,例如apt install build-essential gdb等。
设置断点后,通过F5进行调试。
图 6 Vscode中对单个C/C++文件进行调试
Vscode是如何做到的呢?这是通过Debug Configuration的配置完成的。过去,在Visual Studio等IDE中,对C/C++编译的设置,有详细的图形化配置界面,可以设置编译、链接、调试等等过程配置参数,而在Vscode中,所有设置都在launch.json文件中给出。可以看到,C/C++:gcc build and debug active file的配置里,设置了目标程序、当前目录、调试程序(gdb)、启动设置命令(setupCommands)、前置任务(C/C++: gcc build active file)等信息。
图 7 Vscode的launch.json配置
在前置的Task,C/C++:gcc build active file的配置存在于tasks.json里,可以看到,这里同样有命令、参数和目标,同时我们注意到这里添加了-g选项,支持编译过程中的调试符号嵌入。
图 8 Vscode的tasks.json配置
4.3 如何拓展到复杂的C/C++工程
从上述示例,我们可以看到Vscode对简单C/C++文件的编译和调试处理方式,主要是json文件格式的tasks.json和launch.json进行配置。
复杂的C/C++工程典型的特征就是多个文件,多个模块,涉及到分别编译和相互链接,同时涉及到公共动态库的链接等,同时一个项目可能包含多个可执行目标。那么Vscode如何拓展到复杂的C/C++工程开发和调试呢?答案就是借助CMake工具,以跨平台的方式,将复杂工程的构建规则预先设置好。
5 Vscode中的CMake工程
5.1 Make简介
很多开源代码的代码树里都包含一个Makefile的文件,实际上这个文件就是从源代码到可执行代码构建过程的规则描述,可以看做是源代码都是做菜的原材料或者半成品,可以根据Makefile这个“菜单”描述的步骤,“构建”出最终的“菜品”(也就是软件)来。
Makefile的基本格式就是一系列的目标和依赖规则:
Target1:Dependency1
Build Rule1
Target2:Dependency2
Build Rule2
其中Target可以作为其它Target的Dependency,因此要构建一个目标,需要先构建其依赖。这是一个嵌套的过程,而且可以检查不同目标的构建时间戳,和其依赖的时间戳进行比较,只有依赖更改过,才能触发该目标的重新构建,这可以实现大型项目的增量构建,极大地节约时间。
Makefile的构建规则通常对应不同操作系统下不同的开发工具链的命令,为了同时适配Windows、Linux、Mac OS等不同的操作系统,以及不同的工具链(gcc, msvc, clang等),以及不同的IDE(visual studio, eclipse等),CMake应运而生。CMake工具的目标是Cross platform的Make,通过CMake的更简单理解的语言为每个目录的文件撰写CMakeList.txt文件,实现开发环境和依赖的探测,整个工程的构建,例如生成Visual Studio的工程,Makefile的工程,以及Eclipse的工程等。简单来说,CMake提取更高层和更凝练的信息,然后自动地生成makefile/工程文件等更底层的构建规则文件,并且可以实现跨平台。
5.2 CMake简介
CMake工具可以实现复杂工程跨平台的构建规则撰写。通常,在工程主目录下的CMakeList.txt包含Project的定义和依赖环境的检测,例如C/C++工程依赖的其它动态库头文件和动态库链接文件的位置,设置编译配置,编译参数等,再包含各个子目录。在子目录的CMakeList.txt文件中,包含该目录对应的模块的编译目标规则。
基于CMake描述构建规则的项目,可以实现out of source的构建,例如使用CMake的工程,构建命令通常都是:
mkdir build
CMake ..
这样可以实现所有构建过程产生的文件都位于build目录下,不影响外面的源代码树。
5.3 Vscode中的CMake工具集成
CMake和CMake Tools两个插件提供了Vscode中对CMake工程的支持,重点包括基于CMake的项目配置、构建和调试功能。
CMake Tools插件提供了相关的文档说明,值得一读。
图 9 CMake Tools文档链接
5.4 Quick Start
通过Ctrl+Shift+P,选择CMake:quick start可以基于向导,快速添加一个CMake项目,例如可执行文件目标。这会在当前目录,添加CMakeList.txt,添加必要的源文件,以及设置好工程。用户可以在此基础上进行修改。
在使用CMake构建项目之前,需要通过CMake:Select a kit,选择开发工具链,例如gcc/g++。通过CMake:Select Variant,选择项目变体,例如Debug。通过CMake:configure,触发CMake进行配置。
配置好项目后,就可以开始构建项目了,可以采用CMake: Build命令,或者状态栏中的Build按钮。默认情况下构建所有目标,也可以通过CMake: Set Build Target设置需要构建的目标。
所有的CMake状态和目标,都可以从CMake界面中显示出来(CMake: Focus on Project Status View):
图 10 Vscode中CMake插件的项目状态视图
相应的命令:Configure, Build, Test, Debug, Launch 都可以从对应的目标右侧按钮启动。
图 11 Vscode中CMake插件的不同功能按钮
5.5 CMake Tools的更多功能
5.5.1 启动参数
可以在Open User Settings (JSON)命令中,对settings.json进行修改。
图 12 Vscode中打开用户设置命令
例如添加配置阶段的参数,或者构建阶段的参数,设置不同的项目生成器等。
图 13 Vscode中的用户设置
5.5.2 查看配置和构建的命令
通过Show Build Command和Show Configure Command可以查看配置和构建的命令,方便排查问题。
图 14 Vscode中CMake显示构建命令
5.5.3 排查CMake配置问题
可以使用message(STATUS ${target_variables}),打印内部变量的值,方便排查问题。
6 Vscode中的Ascend C算子工程调试
Ascend C算子开发的Hello world工程就是两个张量的加法算子,位于samples/cplusplus/level1_single_api/4_op_dev/6_ascendc_custom_op/kernel_invocation/Add目录下。
图 15 Ascend C自定义算子开发Add算子示例工程
该项目是一个CMake工程,并且提供了run.sh脚本作为项目构建的统一入口(在其中调用CMake构建和运行)。
如果我们希望参考该工程,开发自己的算子,并用Vscode对算子工程进行调试的话,可以利用Vscode基于gdb提供的调试能力,辅助我们快速地调试自定义算子的精度。
6.1 打开Vscode前的准备工作
1 如FAQ所述,如果不希望root用户运行Vscode,需要配置/etc/wsl.conf
2 为了让Ascend C算子能够正确地链接,需要source /usr/local/Ascend/ascend-toolkit/latest/bin/setenv.bash,提前设置好LD_LIBRARY_PATH。
需要注意的是Vscode安装路径通常包含空格,例如export PATH=$PATH:'/mnt/c/Program Files/Microsoft Vscode/bin/',在上面第二步之后,PATH环境变量中的空格后面的部分可能会丢掉,因此需要再次添加Vscode的路径到PATH中。
6.2 打开Vscode进行配置、构建和调试
1 配置
通过Open User Settings (JSON)命令,打开settings.json。
图 16 Vscode中打开用户设置命令
设置CMake配置参数,例如smoke_testcase、ASCEND_PRODUCT_TYPE、ASCEND_CORE_TYPE、ASCEND_RUN_MODE、ASCEND_INSTALL_PATH、generator等。
图 17 Vscode中用户设置AscendC算子工程参数
选择工具链,Select a kit.
图 18 Vscode中选择C/C++工具链
(可选)查看配置命令:Show Configure Command。
图 19 Vscode中查看CMake的配置命令
配置,CMake:configure。
图 20 Vscode中执行CMake的配置
2 构建
通过CMake: set build target命令,设置构建目标为add_custom_cpu。
图 21 Vscode中设置CMake构建目标
(可选)查看构建命令,CMake:show build command。
图 22 Vscode中查看CMake构建命令
通过CMake: buid,构建目标,或者点击camke status view中的build按钮。
图 23 Vscode中CMake成功构建目标
3 调试
设置断点,注意一定要在ICPU_RUN_KF宏位置设置断点,以及在算子类中设置断点。
图 24 调用核函数前的断点
图 25 算子类方法的断点
调用Python脚本,生成激励数据和真值数据。
python3 add_custom.py
通过CMake: set debug target设置调试目标为add_custom_cpu。
通过CMake: debug命令,开始调试,代码将停在ICPU_RUN_KF位置:
图 26 Vscode中调试时断点停在核函数调用前
在Debug Console中,输入:
-exec set follow-fork-mode child
图 27 Vscode中在调试终端设置和显示不同的gdb选项
然后Continue,程序将进入算子类的第一个单核调用中。
图 28 Vscode中进入算子类调试算子多核实现
gdb调试多进程,有一系列的选项可以进行设置,可以通过show和set进行查看和修改设置。调试多进程的常用设置包括follow-fork-mode child/parent, detach-on-fork on/off, schedule-multiple on/off,用info inferiors 查看进程列表,用attach pid可以绑定进程,设置follow-fork-mode child和detach-on-fork on 可以调试其中的算子进程,同时其它进程挂起,如果需要其它进程继续执行,可以设置schedule-multiple on。
图 29 Vscode中调试Ascend C算子时显示进程列表
7 FAQ
7.1 WSL中启动Vscode,无论是哪个用户启动,得到的都是root用户权限的Vscode和root权限的Terminal?
这是因为Vscode的用户继承自第一个Shell的用户,默认启动wsl是通过root运行的,因此无论su到哪个用户,最终启动Vscode后,都将获得root用户权限。
如果希望改变这一点,可以通过修改/etc/wsl.conf,修改默认用户:
图 30 WSL的示例配置
然后通过wsl.exe --shutdown,关闭wsl后重启,可以指定用户执行Vscode。