GNU,GDB,GCC,G++是什么?与其他编译器又有什么关系?

文章目录


前言

在开始之前我们先放一段Hello World:hello.c

cpp 复制代码
#include <stdio.h>

int main()
{
    printf("Hello World");
    return 0;
}

然后就是一段老生常谈的描述了:要想让这段代码在Linux上运行,我们需要使用GCC预编译:将hello.c和stdio.h预编译为hello.i编译:将hello.i编译为hello.s汇编:将hello.s翻译为机器指令hello.o(.o目标文件)链接:链接各种需要的库和其他目标文件(该hello程序不需要)得到可执行文件hello.out(相当于windows的.exe)整个过程将高级语言翻译成了机器语言,而编译器,就是这样的一个工具。GCC可以完成从预编译编译,汇编,链接整个过程。但是平时使用Visual Studio等软件时并没有接触到这个过程,因为VS是高度集成开发环境(IDE、Integrated Development Environment),集成了代码编辑器,编译器,调试器和图像化用户界面,上述所有程序编译和链接过程都用一步build构建带过了。

1. GNU和他的工具

首先GNU是什么呢,GNU计划,又称革奴计划,是由Richard Stallman在1983年9月27日公开发起的。它的目标是创建一套完全自由的操作系统。因为当时1969年在贝尔实验室诞生的Unix是商业操作系统。

看到这就知道了吧,Stallman便是开源运动的先驱。而他最初的目标"创建一套完全自由的操作系统"也实现了,就是GNU/Linux,简称Linux!

1.1 gcc与g++

gcc 、 g++分别是gnu的c & c++编译器 。

首先我们可以将GCC/G++看成一个整体,不存在GCC专门编译C语言,G++专门编译C++语言这种分别,因为编程语言发展至今是非常复杂的,编译器同样也是。我们将两者都看成GCC,GCC支持C、C++和Fortran语言。而GCC(GNU Compiler Collection,GNU编译器集合),就是GNU运动的代表性成果,它的初衷是为GNU的自由系统开发完整的编译器。所以,在Linux甚至Windows上各种涉及开发环境配置,源码编译的地方,都离不开gcc和g++。

g++的使用示例

1即为生成的文件可以是可执行文件或.a静态库.so动态库,2为生成的命令,生成什么文件,3要编译的文件名,4为头文件包含目录,5为库目录路径,6为库文件名-lmuduo_net即为-l muduo_net

gcc,g++之间的区别

误区:gcc编译c语言,g++编译c++

区别1:

gcc编译c++代码需要加-lstdc++,gcc默认只链接c库,并不会链接c++库,需要手工指定

g++默认链接c库和c++标准库

区别2:

gcc如果编译c语言文件,用c语言方式编译,编译c++用c++方式编译,g++不管编译c还是c++都用c++标方式编译

可执行文件的两种版本

1.debug版本,调试版本,编译阶段会加入某些调试信息 编译时,加入-g选项,可生成debug版本

2.release版本,发行版本,没有调试信息 gcc默认生成release版本

1.2 gdb

GDB 全称"GNU symbolic debugger",从名称上不难看出,它诞生于 GNU 计划(同时诞生的还有 GCC、Emacs 等),是 Linux 下常用的程序调试器。发展至今,GDB 已经迭代了诸多个版本,当下的 GDB 支持调试多种编程语言编写的程序,包括 C、C++、Go、Objective-C、OpenCL、Ada 等。实际场景中,GDB 更常用来调试 C 和 C++ 程序。

使用GDB调试程序,有以下两点需要注意:

要使用GDB调试某个程序,该程序编译时必须加上编译选项 -g,否则该程序是不包含调试信息的;

GCC编译器支持 -O 和 -g 一起参与编译。GCC编译过程对进行优化的程度可分为5个等级,分别为 :

  • -O/-O0: 不做任何优化,这是默认的编译选项 ;
  • -O1:使用能减少目标文件大小以及执行时间并且不会使编译时间明显增加的优化。 该模式在编译大型程序的时候会花费更多的时间和内存。在 -O1下:编译会尝试减少代 码体积和代码运行时间,但是并不执行会花费大量时间的优化操作。
  • -O2:包含 -O1的优化并增加了不需要在目标文件大小和执行速度上进行折衷的优化。 GCC执行几乎所有支持的操作但不包括空间和速度之间权衡的优化,编译器不执行循环 展开以及函数内联。这是推荐的优化等级,除非你有特殊的需求。 -O2会比 -O1启用多 一些标记。与 -O1比较该优化 -O2将会花费更多的编译时间当然也会生成性能更好的代 码。
  • -O3:打开所有 -O2的优化选项并且增加 -finline-functions, -funswitch-loops,-fpredictive-commoning, -fgcse-after-reload and -ftree-vectorize优化选项。这是最高最危险 的优化等级。用这个选项会延长编译代码的时间,并且在使用 gcc4.x的系统里不应全局 启用。自从 3.x版本以来 gcc的行为已经有了极大地改变。在 3.x,,-O3生成的代码也只 是比 -O2快一点点而已,而 gcc4.x中还未必更快。用 -O3来编译所有的 软件包将产生更 大体积更耗内存的二进制文件,大大增加编译失败的机会或不可预知的程序行为(包括 错误)。这样做将得不偿失,记住过犹不及。在 gcc 4.x.中使用 -O3是不推荐的。
  • -Os:专门优化目标文件大小 ,执行所有的不增加目标文件大小的 -O2优化选项。同时 -Os还会执行更加优化程序空间的选项。这对于磁盘空间极其紧张或者 CPU缓存较小的 机器非常有用。但也可能产生些许问题,因此软件树中的大部分 ebuild都过滤掉这个等 级的优化。使用 -Os是不推荐的。

GDB调试主要有三种方式:

直接调试目标程序:gdb ./hello_server

附加进程id:gdb attach pid

调试core文件:gdb filename corename

退出GDB:

可以用命令:q(quit的缩写)或者 Ctr + d 退出GDB。

如果GDB attach某个进程,退出GDB之前要用命令 detach 解除附加进程。

2.Windows的Mingw/MSVC

MinGW(Minimalist GNUfor Windows),它是一个可自由使用和自由发布的Windows特定头文件和使用GNU工具集导入库的集合,允许你在Windows平台生成本地的Windows程序而不需要第三方C运行时(C Runtime)库。运行时库:支持程序运行的基本函数的集合,一般是静态库lib或动态库dll。而MSVC,就是上文所说的第三方C运行时库:由微软开发的VC运行时库,被Visual Studio IDE所集成。所以我们使用VS时会附带MSVC编译器。所以可以看到啦,MinGW和MSVC都是Windows C/C++语言编译支持,配置环境时遇到两者择其一即可。

3.LLVM的clang/clang++

有了前文,对LLVM与clang不用解释应该也知道了。LLVM是构架编译器(compiler)的框架系统,以C++编写而成,用于优化以任意程序语言编写的程序的编译时间(compile-time)、链接时间(link-time)、运行时间(run-time)以及空闲时间(idle-time),对开发者保持开放,并兼容已有脚本。LLVM计划启动于2000年,最初由美国UIUC大学的Chris Lattner博士主持开展。2006年Chris Lattner加盟Apple Inc.并致力于LLVM在Apple开发体系中的应用。Apple也是LLVM计划的主要资助者。目前LLVM已经被苹果IOS开发工具、Xilinx Vivado、Facebook、Google等各大公司采用。

4.Make/CMake

有了编译器GCC等等, 为什么要有make这个构建生成器,同样是老生常谈的内容。编译hello.c非常简单,只需要$ gcc hello.c就可以了,但当项目庞大起来后,假设hello.c依赖与a.c、b.c,而a.c又依赖于库w.lib,每一次编译,我们都要重新编写一次gcc编译命令行吗?所以,GNU发明了make这个工具软件,可以编写makefile文件来指定特定的项目构建过程,当项目一个文件的代码更改时,我们只需要重新make一下就可以了。但make依然有很多不足,比如make对于类unix系统是通用的,但对windows系统并不友好(不能跨平台)make语法简单,也就导致了它功能的限制不同编译器的语法规则不同,编写的makefile语法如果适合GCC则不适合MSVC所以,CMake就应运而生啦。CMake是比Make更高一层的工具,Make是编写对应编译器的makefile从而实现编译,而CMake是写一份独立的CmakeList.txt文件,然后该文件会根据当前系统环境选择适合的构建生成器(如VS或者make),然后将CmakeList.txt翻译为适合的文件,再进一步调用系统编译器进行项目构建。

相关推荐
pp-周子晗(努力赶上课程进度版)25 分钟前
【Linux】线程ID、线程管理、与线程互斥
linux·运维·服务器·开发语言
结衣结衣.1 小时前
【MySQL】数据类型
linux·数据库·sql·mysql
萑澈1 小时前
深入探索 Unix 与 Linux:历史、内核及发行版
linux·服务器·unix
天堂的恶魔9461 小时前
C++项目 —— 基于多设计模式下的同步&异步日志系统(4)(双缓冲区异步任务处理器(AsyncLooper)设计)
开发语言·c++·设计模式
未来之窗软件服务2 小时前
数字人,磁盘不够No space left on device,修改python 执行环境-云GPU算力—未来之窗超算中心
linux·开发语言·python·数字人
Zhuai-行淮2 小时前
施磊老师基于muduo网络库的集群聊天服务器(二)
开发语言·网络·c++
爱学习的大牛1232 小时前
Linux 内核开发/测试工具对比 Windows 驱动验证工具 (Driver Verifier)
linux·测试工具·内核
ChoSeitaku2 小时前
NO.97十六届蓝桥杯备战|数论板块-最大公约数和最小公倍数|欧几里得算法|秦九韶算法|小红的gcd(C++)
c++·算法·蓝桥杯
杰肥啊2 小时前
【网络】通过Samba实现Window挂在Linux服务器路径
linux·服务器·网络