C语言程序运行需要的两大环境《C语言进阶》

目录

 程序的翻译环境和执行环境

翻译环境分为两部分,编译+链接

第一步:预编译(预处理)

第二步,编译

第三步:汇编

关于运行环境分为四点:

关于链接库


 程序的翻译环境和执行环境

ANSI C(标准C) 的任何一种实现中,存在两个不同的环境。
*第1种是翻译环境。 在这个环境中源代码被转换为可执行的机器指令。
在编译器中(以VS2019为例),我们写的C语言代码都是文本的信息(各种字符串,数据,结构体等),站在人类的角度,我们能够理解,但是计算机不行,代码需要翻译成计算机呢能够识别的指令:二进制指令

*第2种是执行环境。它用于实际执行代码。
代码经过翻译环境后生成的二进制指令代码,由执行环境来执行生成。

代码编译时生成可执行程序时的步骤:

1. 组成一个程序的每个源文件通过编译过程分别转换成目标代码( object code )。
2. 每个目标文件由链接器( linker )捆绑在一起,形成一个单一而完整的可执行程序。
3. 链接器同时也会引入标准 C 函数库中任何被该程序所用到的函数,而且它可以搜索程序员个人的程序库,将其需要的函数也链接到程序中。
简述来说:
每一个源文件(.c),都单独经过编译器进行编译,生成目标文件(.obj),目标文件和链接库再通过链接器的处理(这个过程就叫链接),就生成了可执行程序(.exe)。
如下图

翻译环境分为两部分,编译+链接

  

编译本身也分为几个阶段:预处理 , 编译 ,汇编。

 接下来我们用一个简单的代码,源文件名(test.c),使用gcc这个编辑器,给大家演示整个过程;

第一步:预编译(预处理)

预编译的指令是:gcc 源文件.c -E - 源文件名 + .i 

1. 预处理 选项 gcc - E test.c - o test.i
预处理完成之后就停下来,预处理之后产生的结果都放在 test.i文件中,具体内容可看下图。

如下面的代码:

源文件文件名 :test.c#include<stdio.h>//定义全局变量,赋值2023
int year = 2023;
#define M 100
int main()
{int a = M;printf("%d\n", M);return 0;
}

1.输入指令gcc test.c -E -test i

终端输出:


2.观察test.c和test .i的内容


 3.在test.i文件中查看

我们发现,在test.i整个代码的末尾,才是我们源代码的内容,那前面的几百行代码又是什么呢,是头文件<stdio.h>的整个内容包含进来了。同时细心的同学发现,test.i中没有了注释,也没有了宏定义的符号M了,所以预处理的作用是:

  1. 注释的删除
  2. #include<stddio.h>头文件的包含
  3. #define 符号的替换
  4. 文本操作
  5. 所以的预处理指令都是在预处理阶段处理的

第二步,编译

编译指令:gcc -S 源文件.c / gcc -S 源文件名 + .i

编译 选项 gcc - S test.c
编译 选项 gcc -S test.i   (编译时,这两个文件都可以输入指令中,都会生成文件test.s)
编译完成之后就停下来,结果保存在 test.s 中。
我们输入  gcc - S test.c 为例

1.输入指令gcc -S test.c / gcc -S test.i

终端输出:


2.生成了test.s文件的内容并展示test.s文件的内容

 


3.总结:

上面黄圈部分就是test.s的内容,里面就是汇编指令。编译的作用是:把c语言代码翻译成汇编指令 。编译的方式是通过:语法分析,词法分析,语义分析,符号汇总等方式。总的来说,编译就是把我们的c语言代码拆解分析,然后翻译成汇编指令给下一步汇编的动作。

第三步:汇编

汇编指令:gcc -c 源文件.c / gcc -c 源文件名 + .s

汇编 gcc - c test.c
汇编完成之后就停下来,结果保存在 test.o 中。

 1.输入指令gcc -c test.c / gcc-c test.s

终端输出:


 

2.生成了test.o的目标文件

但是你会发现这是test.o目标文件存放的二进制文件,编译器是不支持显示的的,如果仍要打开,如下图;


 


 3. 总结:

1.目标文件中存放的是二进制的指令

2.汇编是把汇编指令翻译成二进制指令

顺便提一下:Linux下gcc编译产生的目标文件test.o,可执行程序test都是按照ELF的这种文件格式存储的 

最后,以上过程完成了编译,之后到链接过程

链接指令:gcc 源文件名.o -o 新文件名 

对目标文件进行链接。可生成一个可执行文件

 1.输入指令:gcc test.o -o vskkk

输出终端:


2,对vskkk的内容进行查看

 但是文件还是二进制的指令无法查看。


3.总结:

链接的作用是:

1.合并线段

2.符号表的合并和重定位

 


关于运行环境分为四点:

运行环境相较于翻译环境就好理解的多了,通俗理解有以下几点:

1. 程序必须载入内存中。在有操作系统的环境中:一般这个由操作系统完成。在独立的环境中,程序的载入必须由手工安排,也可能是通过可执行代码置入只读内存来完成。
2. 程序的执行便开始。接着便调用 main 函数。
3.开始执行程序代码。这个时候程序将使用一个运行时堆栈(stack),存储函数的局部变量和回
地址。程序同时也可以使用静态( static )内存,存储于静态内存中的变量在程序的整个执行过程
一直保留他们的值。
4. 终止程序。正常终止 main 函数;也有可能是意外终止。

关于链接库

我们知道再写C语言代码时,只要加上头文件 #include<stdio.h> ,就可以直接使用库函数了,比如scanf(),printf(),那为什么可以直接使用呢?原因是我们把这些库函数都已经提前编译好,打包好放在静态库中,可以直接提供给我们,比如我们熟悉的scanf函数,如下图的打红圈内容,标记部分后缀以LIB结尾的,就是静态库(.LIB),库函数的静态库和目标文件在链接器中发生链接生成可执行程序。程序就可以运行啦。


以上就是全部内容了,希望能帮助到大家,如果可以,也希望大家给博主点点赞支持一下,谢谢。如果有错误的地方,希望大家能在评论区批评指出,我会进行订正的。

 

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

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

相关文章

【全面解析】Windows 如何使用 SSH 密钥远程连接 Linux 服务器

创建密钥 创建 linux 服务器端的终端中执行命令 ssh-keygen&#xff0c;之后一直按Enter即可&#xff0c;这样会在将在 ~/.ssh/ 路径下生成公钥(id_rsa.pub)和私钥(id_rsa) 注意&#xff1a;也可以在 windows 端生成密钥&#xff0c;只需要保证公钥在服务器端&#xff0c;私钥…

Apache Struts2漏洞复现之s2-001漏洞复现

0x01 声明&#xff1a; 仅供学习参考使用&#xff0c;请勿用作违法用途&#xff0c;否则后果自负。 0x02 简介&#xff1a; Apache Struts 2是一个用于开发Java EE网络应用程序的开放源代码网页应用程序架构。它利用并延伸了Java ServletAPI&#xff0c;鼓励开发者采用MVC架构…

Android ObjectBox数据库的使用与详解

一、介绍 Room数据库 之前我已介绍了jetpack组件的数据库&#xff1a;Room&#xff0c;有小伙伴需要了解Room数据库可以查看这个地址&#xff1a;Android JetPack组件之Room数据库的集成与详解_android room数据库_蜗牛、Z的博客-CSDN博客 数据库的性能对设备来说很重要&#…

安全开发-JS应用原生开发JQuery库Ajax技术加密编码库断点调试逆向分析元素属性操作

文章目录 JS原生开发-文件上传-变量&对象&函数&事件JS导入库开发-登录验证-JQuery库&Ajax技术JS导入库开发-编码加密-逆向调试 JS原生开发-文件上传-变量&对象&函数&事件 1、布置前端页面 2、JS获取提交数据 3、JS对上传格式判断 <script>…

抖音seo开源源码,抖音优化系统定制方案

抖音作为目前最火热的短视频平台之一&#xff0c;其在移动互联网领域的影响越来越大。然而&#xff0c;一款成功的产品未必仅仅靠着其自身的功能和品质就能获得市场的认可&#xff0c;还需要通过优化SEO来实现更好的曝光率。下面&#xff0c;本文将介绍如何优化抖音SEO源码开发…

Vue3通透教程【十六】TS编译配置

文章目录 &#x1f31f; 写在前面&#x1f31f; 初始化配置文件⭐ target⭐ module⭐ lib⭐ types/node⭐ include⭐ outDir&#x1f31f; 写在最后 &#x1f31f; 写在前面 专栏介绍&#xff1a; 凉哥作为 Vue 的忠实 粉丝输出过大量的 Vue 文章&#xff0c;应粉丝要求开始更…

【英杰送书第三期】Spring 解决依赖版本不一致报错 | 文末送书

Yan-英杰的主 悟已往之不谏 知来者之可追 C程序员&#xff0c;2024届电子信息研究生 目录 问题描述 报错信息如下 报错描述 解决方法 总结 【粉丝福利】 【文末送书】 目录&#xff1a; 本书特色&#xff1a; 问题描述 报错信息如下 Description:An attempt…

Data Transfer Object-DTO,数据传输对象,前端参数设计多个数据表对象

涉及两张表的两个实体对象 用于在业务逻辑层和持久层&#xff08;数据库访问层&#xff09;之间传输数据。 DTO的主要目的是将多个实体&#xff08;Entity&#xff09;的部分属性或多个实体关联属性封装成一个对象&#xff0c;以便在业务层进行数据传输和处理&#xff0c;从而…

Python 算法基础篇:冒泡排序和选择排序

Python 算法基础篇&#xff1a;冒泡排序和选择排序 引言 1. 冒泡排序算法概述2. 冒泡排序算法实现实例1&#xff1a;冒泡排序 3. 选择排序算法概述4. 选择排序算法实现实例2&#xff1a;选择排序 5. 冒泡排序与选择排序的对比总结 引言 冒泡排序和选择排序是两种常用的排序算法…

高校大数据教材推荐-《Python中文自然语言处理基础与实战》

《Python中文自然语言处理基础与实战》是“十四五”职业教育国家规划教材&#xff0c;是大数据应用开发&#xff08;Python&#xff09;“1X”职业技能等级证书配套系列教材。本书以项目为载体&#xff0c;突出职业技能。坚持理实一体化的理念。理实一体化&#xff0c;就是理论…

iOS--虚拟内存

参考文章 要想了解什么是VM Regions&#xff0c;就得先了解什么是虚拟内存。当我们向系统申请内存时&#xff0c;系统并不会给你返回物理内存的地址&#xff0c;而是给你一个虚拟内存地址。每个进程都拥有相同大小的虚拟地址空间&#xff0c;对于32位的进程&#xff0c;可以拥有…

面试 | 双法妙解压缩字符串【遍历统计 + 双指针】

一、题目描述 原题传送门 二、思路分析 首先我们来分析一下解决本题所需要的思路 题目的意思很简单&#xff0c;就是统计原本的字符串中的每个字符出现的次数&#xff0c;然后以【字符&#xff0c;出现的次数】这样的结构来字符串&#xff0c;以起到一个压缩的效果&#xff0c…

网络安全:密码学基本理论.

网络安全&#xff1a;密码学基本理论. 密码学是研究编制密码和破译密码的技术科学。研究密码变化的客观规律&#xff0c;应用于编制密码以保守通信秘密的&#xff0c;称为编码学&#xff1b;应用于破译密码以获取通信情报的&#xff0c;称为破译学&#xff0c;总称密码学. 目录…

ffmpeg离线安装ffmpeg-4.1.4-amd64-static.tar.xz

1.下载离线包 John Van Sickle - FFmpeg Static Builds 找历史版本&#xff1a;Index of /ffmpeg/old-releases 我选择是的4.1.4版本 2.解压 tar -xvJf ffmpeg-4.1.4-amd64-static.tar.xz 3.移动文件到opt目录下 4.添加全局链接 ln -s /opt/ffmpeg-4.1.4-amd64-static/ffm…

在macOS、Windows上使用VSCode + SSH实现远程Matplotlib图形显示

简介 在 macOS 上使用 VSCode SSH 环境来显示 Matplotlib 绘制的图形需要进行一些配置。因为默认情况下&#xff0c; Matplotlib 的图形是无法显示在远程计算机的桌面上的。您可以通过设置 Matplotlib 使用不同的后端(backend)来实现将图形显示在本地计算机上。 第一步&…

Docker安装Nacos2.0.2

docker拉取镜像 docker pull nacos/nacos-server:2.0.2查看镜像 docker images创建容器和运行 docker run -e JAVA_OPTS"-Xms256m -Xmx256m" -e MODEstandalone -e PREFER_HOST_MODEhostname -p 8848:8848 --privilegedtrue --restartalways --name nacos -d naco…

小程序制作教程

步骤一&#xff1a;规划和设计 在开始制作微信小程序之前&#xff0c;首先需要规划和设计您的小程序。确定您想要提供的服务或功能&#xff0c;并考虑用户体验和界面设计。绘制草图和构思完整的页面布局&#xff0c;这将使您更好地理解小程序结构和功能。 步骤二&#xff1a;…

Python Selenium设计模式及代码实现

前言 本文就python selenium自动化测试实践中所需要的POM设计模式进行分享&#xff0c;以便大家在实践中对POM的特点、应用场景和核心思想有一定的理解和掌握。 为什么要用POM 基于python selenium2开始UI级自动化测试并不是多么艰巨的任务。**只需要定位到元素&#xff0c;…

公网访问的Linux CentOS本地Web站点搭建指南

文章目录 前言1. 本地搭建web站点2. 测试局域网访问3. 公开本地web网站3.1 安装cpolar内网穿透3.2 创建http隧道&#xff0c;指向本地80端口3.3 配置后台服务 4. 配置固定二级子域名5. 测试使用固定二级子域名访问本地web站点 前言 在web项目中,部署的web站点需要被外部访问,则…

基于SPDK-vhost的云原生Kubevirt虚拟化存储IO的优化方案

摘要 本文主要介绍针对云原生kubernetes虚拟化IO的应用场景&#xff0c;在Kubevirt中引入SPDK-vhost的支持&#xff0c;来加速虚机中IO存储性能。同时基于Intel开源的Workload Service Framework[1]平台集成部署一套端到端虚拟化IO的应用场景做基本的性能对比测试。 云原生Kube…