嵌入式Linux学习第二天

今天学习linuxC编程。首先要熟悉linux下编写c程序的过程。

编写程序Hello World!

首先创建存放程序的文件夹,如下图所示:
在这里插入图片描述
接下来在创建一个文件夹来保存这节要编写的代码。指令:mkdir 3.1
在这里插入图片描述
接下来我们要设置VIM编辑器的一些配置,比如设置tab的字符数为4、以及设置VIM编辑器的行号。在文件/etc/vim/vimrc 中添加代码:

set nu
set ts=4

然后创建main.c文件。
在这里插入图片描述
编写程序完事后,使用“gcc main.c –o main”来编译 main.c 文件,使用参数“-o”来指定编译生成的可执行文件名字。
在这里插入图片描述

GCC编译器

gcc 命令

在上一小节我们已经使用过 GCC 编译器来编译 C 文件了,我们使用到是 gcc 命令,gcc 命令格式如下:

gcc [选项] [文件名字]
主要选项如下:
-c:只编译不链接为可执行文件,编译器将输入的.c 文件编译为.o 的目标文件。
-o:<输出文件名>用来指定编译结束以后的输出文件名,如果不使用这个选项的话 GCC 默
认编译出来的可执行文件名字为 a.out。
-g:添加调试信息,如果要使用调试工具(如 GDB)的话就必须加入此选项,此选项指示编
译的时候生成调试所需的符号信息。
-O:对程序进行优化编译,如果使用此选项的话整个源代码在编译、链接的的时候都会进
行优化,这样产生的可执行文件执行效率就高。
-O2:比-O 更幅度更大的优化,生成的可执行效率更高,但是整个编译过程会很慢。

编译流程

GCC 编译器的编译流程是:预处理、编译、汇编和链接。预处理就是展开所有的头文件、替换程序中的宏、解析条件编译并添加到文件中。编译是将经过预编译处理的代码编译成汇编代码,也就是我们常说的程序编译。汇编就是将汇编语言文件编译成二进制目标文件。链接就是将汇编出来的多个二进制目标文件链接在一起,形成最终的可执行文件,链接的时候还会涉及到静态库和动态库等问题。上一小节演示的例程都只有一个文件,而且文件非常简单,因此可以直接使用 gcc 命令生成可执行文件,并没有先将 c 文件编译成.o 文件,然后再链接在一起。

Makefile 基础

当文件有几十、上百甚至上万个的时候用终端输入 GCC 命令的方法显然是不现实的。如果我们能够编写一个文件,这个文件描述了编译哪些源码文件、如何编译那就好了,每次需要编译工程的时只需要使用这个文件就行了。这种问题怎么可能难倒聪明的程序员,为此提出了一个解决大工程编译的工具:make,描述哪些文件需要编译、哪些需要重新编译的文件就叫做 Makefile,Makefile 就跟脚本文件一样,Makefile 里面还可以执行系统命令。使用的时候只需要一个 make命令即可完成整个工程的自动编译,极大的提高了软件开发的效率。如果大家以前一直使用 IDE来编写 C 语言的话肯定没有听说过 Makefile 这个东西,其实这些 IDE 是有的,只不过这些 IDE对其进行了封装,提供给大家的是已经经过封装后的图形界面了,我们在 IDE 中添加要编译的
C 文件,然后点击按钮就完成了编译。在 Linux 下用的最多的是 GCC 编译器,这是个没有 UI的编译器,因此 Makefile 就需要我们自己来编写了。

Makefile 语法

Makefile 规则格式
Makefile 里面是由一系列的规则组成的,这些规则格式如下:

目标…... : 依赖文件集合……
命令 1
命令 2
……
main : main.o input.o calcu.ogcc -o main main.o input.o calcu.o

第一行定义了一个规则,它告诉make命令如何构建目标main。在这里,main是一个目标(通常是最终要生成的程序或文件),而main.o、input.o和calcu.o是这个目标的依赖项,意味着在构建main之前,必须首先存在或构建这些依赖项。

目标(target):main是这条规则的目标,也就是这条规则想要构建或更新的文件。
依赖(dependencies):main.o、input.o和calcu.o是目标的依赖项,这意味着在尝试构建main之前,make会确保所有的依赖项都是最新的。
gcc是GNU编译器集合中的C编译器,用于编译C语言程序。-o main选项告诉gcc将链接生成的可执行文件命名为main。main.o、input.o和calcu.o是gcc需要链接的对象文件。这些对象文件之前已经由gcc从相应的源文件编译生成。
命令列表中的每条命令必须以 TAB 键开始,不能使用空格!
make 命令会为 Makefile 中的每个以 TAB 开始的命令创建一个 Shell 进程去执行。了解了 Makefile 的基本运行规则以后我们再来分析一下 3.3 节中“示例代码 3.3.2.6”中的Makefile,代码如下:、在这里插入图片描述
上述代码中一共有 5 条规则,1~2 行为第一条规则,3~4 行为第二条规则,5~6 行为第三条规则,7~8 行为第四条规则,10~12 为第五条规则,make 命令在执行这个 Makefile 的时候其执行步骤如下:首先更新第一条规则中的 main,第一条规则的目标成为默认目标,只要默认目标更新了那么就认为 Makefile 的工作。在第一次编译的时候由于 main 还不存在,因此第一条规则会执行,第一条规则依赖于文件 main.o、input.o 和 calcu.o 这个三个.o 文件,这三个.o 文件目前还都没有,因此必须先更新这三个文件。make 会查找以这三个.o 文件为目标的规则并执行。以 main.o为例,发现更新 main.o 的是第二条规则,因此会执行第二条规则,第二条规则里面的命令为“gcc–c main.c”,这行命令很熟悉了吧,就是不链接编译 main.c,生成 main.o,其它两个.o 文件同理。最后一个规则目标是 clean,它没有依赖文件,因此会默认为依赖文件都是最新的,所以其对应的命令不会执行,当我们想要执行 clean 的话可以直接使用命令“make clean”,执行以后就会删除当前目录下所有的.o 文件以及 main,因此 clean 的功能就是完成工程的清理,
总结一下 Make 的执行过程:
1、make 命令会在当前目录下查找以 Makefile(makefile 其实也可以)命名的文件。
2、当找到 Makefile 文件以后就会按照 Makefile 中定义的规则去编译生成最终的目标文件。
3、当发现目标文件不存在,或者目标所依赖的文件比目标文件新(也就是最后修改时间比目标文件晚)的话就会执行后面的命令来更新目标。
在这里插入图片描述
原子文档总结的很形象。具体执行的过程就如上图所示:

Makefile 变量

跟 C 语言一样 Makefile 也支持变量的,先看一下前面的例子:

 main: main.o input.o calcu.ogcc -o main main.o input.o calcu.o

上述 Makefile 语句中,main.o input.o 和 calcue.o 这三个依赖文件,我们输入了两遍,我们这个 Makefile 比较小,如果 Makefile 复杂的时候这种重复输入的工作就会非常费时间,而且非常容易输错,为了解决这个问题,Makefile 加入了变量支持。不像 C 语言中的变量有 int、char等各种类型,Makefile 中的变量都是字符串!类似 C 语言中的宏。使用变量将上面的代码修改,修改以后如下所示:

1 #Makefile 变量的使用
2 objects = main.o input.o calcu.o
3 main: $(objects)
4 gcc -o main $(objects)

第 1 行是注释,Makefile 中可以写注释,注释开头要用符号“#”,不能用 C 语言中的“//”或者“/**/”!第 2 行我们定义了一个变量 objects,并且给这个变量进行了赋值,其值为字符串“main.o input.o calcu.o”,第 3 和 4行使用到了变量 objects,Makefile 中变量的引用方法是“ ( 变量名 ) ”,比如本例中的“ (变量名)”,比如本例中的“ (变量名),比如本例中的(objects)”就是使用变量 objects。在“示例代码 3.4.2.1”中我们在定义变量 objects 的时候使用“=”对其进行了赋值,Makefile变量的赋值符还有其它两个“:=”和“?=”,我们来看一下这三种赋值符的区别:
1、赋值符“=”
示例代码 3.4.2.1 赋值符"="使用

1 name = zzk
2 curname = $(name)
3 name = zuozhongkai
4
5 print:
6 @echo curname: $(curname)

2、赋值符“:=”
赋值符“:=”不会使用后面定义的变量,只能使用前面已经定义好的,这就是“=”和“:=”两个的区别。
3、赋值符“?=”
“?=”是一个很有用的赋值符,比如下面这行代码:

curname ?= zuozhongkai

上述代码的意思就是,如果变量 curname 前面没有被赋值,那么此变量就是“zuozhongkai”,
如果前面已经赋过值了,那么就使用前面赋的值。
4、变量追加“+=”
Makefile 中的变量是字符串,有时候我们需要给前面已经定义好的变量添加一些字符串进
去,此时就要使用到符号“+=”,比如如下所示代码:

objects = main.o input.o
objects += calcu.o

一开始变量 objects 的值为“main.o input.o”,后面我们给他追加了一个“calcu.o”,因此变量 objects 变成了“main.o input.o calcu.o”,这个就是变量的追加。

Makefile 模式规则

模式规则中,至少在规则的目标定定义中要包涵“%”,否则就是一般规则,目标中的“%”表示对文件名的匹配,“%”表示长度任意的非空字符串,比如“%.c”就是所有的以.c 结尾的文件,类似与通配符,a.%.c 就表示以 a.开头,以.c 结束的所有文件。
当“%”出现在目标中的时候,目标中“%”所代表的值决定了依赖中的“%”值,

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.hqwc.cn/news/670648.html

如若内容造成侵权/违法违规/事实不符,请联系编程知识网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

CST电磁仿真计算热损耗和人体比吸收率【基础教程】

结果合并 获取不同输入条件下的结果! Post-Processing >2D/3D Field Post-Processing > Combine Results 设计类似阵列天线的多端口RF系统时&#xff0c;各Port分别定义输入特性就可查看多端口合并得到Combine Results。进行All Ports Simulation之后无需再运行仿真&am…

2024第2届华东国际宠物用品展(苏州)

第2届华东宠物展&#xff08;苏州&#xff09;2024.06.28-30 苏州国际博览中心 中国宠业新锐品牌展 400海外展商 20000平方展出面积 3000知名品牌 60000优质观众 参展组委会咨询&#xff1a;深宠展邹春宇 关于展会 第2届华东国际宠物用品展览会(苏州)暨中国宠业新锐品牌…

2023ccpc深圳G题相似基因序列问题

样例&#xff1a; 6 4 4 1 kaki kika manu nana tepu tero kaka mana teri anan 输出&#xff1a; 2 2 1 0 解析&#xff1a; 如果是用暴力的话是 300*300*6000&#xff0c;这样子一定会超时。 这时候我们可以利用hash函数进行处理&#xff0c;对比一个字符串的小于为O&a…

SCI一区 | WOA-BiTCN-BiGRU-Attention多输入单输出回归预测(Matlab)

SCI一区 | WOA-BiTCN-BiGRU-Attention多输入单输出回归预测&#xff08;Matlab&#xff09; 目录 SCI一区 | WOA-BiTCN-BiGRU-Attention多输入单输出回归预测&#xff08;Matlab&#xff09;效果一览基本介绍程序设计参考资料 效果一览 基本介绍 1.Matlab实现WOA-BiTCN-BiGRU-A…

【go项目01_学习记录05】

学习记录 1 依赖管理 Go Modules1.1 弃用 $GOPATH1.2 Go Modules 日常使用1.2.1 初始化生成go.mod文件1.2.2 Go Proxy代理1.2.3 go.mod文件查看1.2.4 go.sum文件查看1.2.5 indirect 含义1.2.6 go mod tidy 命令1.2.7 清空 Go Modules 缓存1.2.8 下载依赖1.2.9 所有 Go Modules …

通信系列:通信中如何度量消息中所包含的信息量?如何评估通信系统的性能?

微信公众号上线&#xff0c;搜索公众号小灰灰的FPGA,关注可获取相关源码&#xff0c;定期更新有关FPGA的项目以及开源项目源码&#xff0c;包括但不限于各类检测芯片驱动、低速接口驱动、高速接口驱动、数据信号处理、图像处理以及AXI总线等 本节目录 一、通信中如何度量消息…

【Linux网络编程】自定义协议+HTTP协议

【Linux网络编程】自定义协议HTTP协议 目录 【Linux网络编程】自定义协议HTTP协议协议定制&#xff0c;序列化和反序列化应用层中的HTTP认识URL&#xff08;网址&#xff09;urlencode和urldecodeHTTP协议格式使用telnet获取百度的根目录资源HTTP的方法表单 HTTP的状态码HTTP常…

昂科烧录器支持O2Micro凹凸科技的电池组管理IC OZ7708

芯片烧录行业领导者-昂科技术近日发布最新的烧录软件更新及新增支持的芯片型号列表&#xff0c;其中O2Micro凹凸科技的电池组管理IC OZ7708已经被昂科的通用烧录平台AP8000所支持。 OZ7708是一款高度集成、低成本的电池组管理IC&#xff0c;适用于5~8s Li-Ion/Polymer电池组&a…

负氧离子大气监测系统解析

TH-FZ5负氧离子大气监测系统是一个综合性的环境监测系统&#xff0c;主要用于实时监测和评估大气中负氧离子的浓度水平。负氧离子&#xff0c;也称为空气维生素&#xff0c;对人体健康和环境质量有重要影响。负氧离子大气监测系统通常包括以下几个主要组成部分&#xff1a; 负氧…

Transformer - 编码器和解码器中的QKV分别来自哪

Transformer - 编码器和解码器中的QKV分别来自哪 flyfish Transformer - 注意⼒机制 Scaled Dot-Product Attention 计算过程 Transformer - 注意⼒机制 代码实现 Transformer - 注意⼒机制 Scaled Dot-Product Attention不同的代码比较 Transformer - 注意⼒机制 代码解释 Tr…

jetson实操(二):jetson nano发送短信到指定用户

文章目录 一、准备工作二、代码实现 一、准备工作 腾讯云网址&#xff1a;点击 注&#xff1a;需先申请“短信签名”和“短信正文”&#xff0c;按照要求填写申请即可&#xff0c;腾讯云的审核效率还是很快的&#xff0c;一般在1-2个小时内就会有结果&#xff0c;链接&…

Vue中Element的下载

打开vscode让项目在终端中打开 输入npm install element-ui2.15.3 然后进行下载 在node_modules中出现element-ui表示下载完成 然后在输入Vue.use(ElementUI); import Vue from vue import App from ./App.vue import router from ./router import ElementUI from element-ui…