CUDA02_01Window10C开发环境
算算差不多6年时间没有玩过Window了,从DOS3.0开始,到Window3.1,到Window95,NT,Window ME,WindowXP,Window 2000 Server。后面的就没有正经使用过Window。开发工具,从Microsoft C++ 4到 VC++6.0,用过C++ Builder,VB,PB,ASP,DCOM,Win32, MFC,ActiveX,OLE,VBA,DirectX,C#,.......。当年也是微软的拥揼者,微软一直想像IBM,Oracle一样分杯企业市场,遗憾的是还是没有成功,还是在个人市场独大。
这个主题整理下微软C/C++开发的环境。主要回顾了cl
,link
,lib
,nmake
几个工具的使用。
Window的C++编译器
- Window下C++编译器能选择的常见就两款
- Microsoft C++ Compiler
- 通过安装VStudio可以得到;
- MinGW C++ Compiler
- 下载路径:
http://www.mingw.org/category/wiki/download
- 其他API库下载:
https://osdn.net/projects/mingw/releases/
- 使用下载管理器完成安装也可:
https://osdn.net/projects/mingw/downloads/68260/mingw-get-setup.exe/
- 下载路径:
- 注意:
- 在Window下,我们还是使用微软家的Visual Stduio IDE吧。
- Microsoft C++ Compiler
Microsoft Compiler编译器与开发工具使用
编译器相关工具
-
Microsoft的编译工具包含三个核心工具
- 编译器cl
- 连接器link
- 库生成工具lib
-
测试编译器的代码
- 文件名:
c01_readbmp.c
- 文件名:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
int main(int argc, char const *argv[]){
// 打开文件
FILE* file = fopen("gpu.bmp", "rb");
// 判定文件是否打开成功
if(!file){
printf("打开文件失败!\n");
exit(EXIT_FAILURE);
}
printf("打开文件成功!\n");
// 读取文件的前两个字节
unsigned char c_magic[3] = {0};
size_t sz_return = fread(c_magic, 1, 2, file);
printf("读取的字节数:%zd\n", sz_return);
if(!strcmp(c_magic, "BM")){
printf("文件是BMP文件!\n");
}else{
printf("文件不是BMP文件!\n");
}
// 关闭文件
fclose(file);
return 0;
}
-
最简单的编译链接:
cl c01_readbmp.c
-
直接生成与源代码一样文件名的exe执行文件。
编译链接产生执行文件
-
学习微软编译器的最好方法就是去VS IDE工具中找对应的设置;
这些命令行在IDE中都可视化配置
- 下面分开来解释下链接编译过程
- cl编译器
-
编译器工作包含两个阶段:
- 预编译(处理宏替换与预处理指令)
- 编译(编译成目标文件.obj文件)
-
下面演示都是在VS IDE提供的环境中执行:
- 意味着INCLUDE与LIBPATH已经被设置。
-
与编译只与头文件有关,并且检测语法
- 与动态库与静态库无关;
-
编译演示:
cl /c /Fo输出的目标文件名 源代码文件
cl /c /Foc01.obj c01_readbmp.c
- 注意:
- 不适用/Fo会输出默认与源代码文件名相同的目标文件,扩展名是obj。
-
/Fo与目标文件名之间不能有空格。
预编译
-
提示:
- 使用/nologo可以去掉logo输出。可以看下面效果。
-
预编译使用选项/E与/P,/EP
- /E直接输出到标准终端
- /P可以预编译输出到指定文件名的文件。
-
/EP输出到标准终端,而且输出行号。
预编译的结果
-
提示:
- 一般预编译的文件的扩展名为i;
- 编译产生的汇编,扩展名为.s;
- 使用/Fa选项:
cl /Fac01.s /nologo c01_readbmp.c
- 使用/Fa选项:
- 目标文件扩展名为.obj;
-
汇编编译结果
编译产生的汇编代码
- link连接器
-
link链接器是直接生成可执行文件
- exe独立执行文件
- 扩展名exe
- dll动态执行文件
- 扩展名dll
- exe独立执行文件
-
提示:
- 链接一般链接一个或者多个目标文件,生成执行文件;
- 链接需要执行文件需要的动态库与静态库;
- 静态库会链接成执行文件的一部分,效果等价于目标文件;
- 动态库在window中还需要导出符号表等信息。
-
链接程序的例子:
-
link c01.obj /out:main.exe
把目标文件链接成执行文件
-
-
link的其他用途:
-
链接动态库
-
导出符号表
-
下面是帮助
link的帮助
-
- lib库编译器
-
lib库编译器是编译成静态库。
- 库的扩展名是lib
-
提示:
- lib编译的不是动态库,而是静态库;
- 静态库的使用比动态库简单多了,这里不演示动态库了;
-
lib使用例子:
- 查看静态库中内容:
lib /list lib库文件
; - 归档目标文件为静态库:
lib /out:输出库文件 目标文件 .......
lib使用例子
- 查看静态库中内容:
编译辅助工具
- nmake工具
-
这是一个解释执行Makefile脚本的工具。
- 语法套路按照Makefile即可,使用与Unix相关的平台的make工具差不多。
-
直接仿照Unix的Makefile编写脚本:
# 执行文件生成
main: c01_readbmp.obj
@link /nologo c01_readbmp.obj /out:main.exe
# 目标文件生成
c01_readbmp.obj:c01_readbmp.c
@cl /nologo /c c01_readbmp.c
# 清除,错误定向到空设备
clean:
@del *.exe *.obj *.i *.s *.lib 2>nul
- 执行编译
nmake main
-
nmake clean
使用namke
附录
- 命令行开发环境
-
使用IDE的可以不用关注这个:
- 在Visual Studio的安装目录下,有一个专门设置C/C++开发环境的脚本,执行后可以不用设置各种环境了。尤其头文件目录,库文件目录。
C:\Program Files (x86)\Microsoft Visual Studio\2019\Enterprise\Common7\Tools\VsDevCmd.bat
-
上面这个脚本是cmd的批处理脚本,只能在cmd控制终端使用。
-
VsDevCmd.bat
会生成几个有用的环境变量,这几个环境变量影响着编译器的行为。INCLUDE
LIBPATH
-
不设置这两个环境变量,请使用编译命令行指定/I选项指定include的搜索路径吧。
-
使用
查看INCLUDE与LIBPATH环境变量set
指令,查看这两个环境变量:
- VSCode下的源代码编码问题
- 目测VSCode对UTF-8工作得不是很好,对UTF-8 BOM工作很好。
- 如果出现如下编译警告,则设置编辑器的编码为UTF-8 BOM,记得关闭文件重新打开,或者重新建立文件。
该文件包含不能在当前代码页(936)中表示的字符。请将该文件保存为 Unicode 格式以防止数据丢失
- 如果出现如下编译警告,则设置编辑器的编码为UTF-8 BOM,记得关闭文件重新打开,或者重新建立文件。
- 关于cmd与powershell的选择
- cmd及其脚本比较古典。
-
powershell明显模仿了bash或者csh,习惯Unix相关操作系统的,可以选择powershell。
使用ls替代dir