本文只为整理思路,供自己日后参考。现在就从从一个执行文件a.out的运行开始,自上而下地分析linux是如何运行一个执行文件的。

1、首先,需要了解一下a.out这个目标文件。a.out在linux下是ELF(Executable Linkable Format)文件格式,该目标文件由一个文件头、代码段、数据段(已初始化)、从定位信息区、符号表及符号名字字符串构成,如下左图所示,经过链接后生成执行文件如下右图所示,需要说明的是1).bss段在目标文件和执行文件中并不占用文件的空间,但是它在加载时占用地址空间;2)链接后各个段在虚拟空间上的地址就确定了,并且linux下,ELF可执行文件默认从地址0x080480000开始分配。

我们知道在linux下运行一个程序只要在shell中执行 ./a.out 这个命令就OK了,剩下的事情操作系统会替我们完成。但是操作系统到底做了什么,它是怎么做的呢,接下来就来解析一下。

2、linux系统中每个程序都运行在一个进程上下文中,这个进程上下文有自己的虚拟地址空间。当shell运行一个程序时,父shell进程生成一个子进程,它是父进程的一个复制品。子进程通过execve系统调用启动加载器。加载器删除子进程已有的虚拟存储段,并创建一组新的代码、数据、堆、栈段,新的堆和栈被初始化为零。通过将虚拟地址空间中的页映射到可执行文件的页大小组块,新的代码和数据段被初始化为可执行文件的内容,最后将CUP指令寄存器设置成可执行文件入口,启动运行。

执行完上述操作后,其实可执行文件的真正指令和数据都没有别装入内存中。操作系统只是通过可执行文件头部的信息建立起可执行文件和进程虚拟内存之间的映射关系而已。现在程序的入口地址为0x08048000,刚好是代码段的起始地址。当CPU打算执行这个地址的指令时,发现页面0x8048000~0x08049000(一个页面一般是4K)是个空页面,于是它就认为是个页错误。此时操作系统根据虚拟地址空间与可执行文件间的映射关系找到页面在可执行文件中的偏移,然后在物理内存中分配一个物理页面,并在虚拟地址页面与物理页面间建立映射,最后把文件中页面拷贝到物理页面,进程重新开始执行。该过程如下图所示:

3、这里比较难理解的就是这个分页机制,讲到分页机制,就不得不提linux的分段与分页机制,这也是这篇文章的重点。我们先来看一张图:

这张图展示了虚拟地址进过分段、分页机制后转化成物理地址的简单过程。其实分段机制是intel芯片为兼容以前产品而保留下来的,然后linux中弱化了这一机制。下面我们先简单介绍一下分段机制:

分段提供了隔绝各个代码、数据和堆栈区域的机制,它把处理器可寻址的线性地址空间划分成一些较小的称为段的受保护地址空间区域。如果处理器中有多个程序在运行,那么每个程序可分配各自的一套段。此时处理器就可以加强这些段之间的界限,并确保一个程序不会通过访问另一个程序的段而干扰程序的执行。为了定位指定段中的一个字节,程序必须提供一个逻辑地址,该地址包括一个段选择符和一个偏移量。实模式下,段值还是可以看作地址的一部分,段值位XXXXh表示以XXXX0h开始的一段内存。而保护模式下,段值仅仅变成了一个索引,只想一个数据结构的一个表项,该表项中定义了段的起始地址、界限、属性等内容。cs、ds等寄存器中存的就是这个段选择符,用段选择符中的段索引在GDT或LDT表中定位相应的段描述符,把段描述符中取得的段基地址加上偏移量,就形成了一个线性地址。

得到了线性地址之后,我们再来看看分页机制如何把它转换成物理地址。处理器分页机制会把线性地址空间(段已映射到其中)划分成页面,然后这些线性地址空间页面被映射到物理地址空间的页面上。分页与分段最大的不同之处在于分页是用来固定长度的页面(一般为4KB)。如果仅适用分段地址转换,那么存储在物理内存中的一个数据结构将包含器所有部分。但如果适用了分页,那么一个数据结构就可以一部分存储在物理内存中,而另一部分保存在磁盘中。

处理器把线性地址转换成物理地址和用于产生页错误异常的信息包含在存储与内存中的页目录和页表中。也变可看作简单的4K为单位的物理地址数组。线性地址的高20位构成这个数组的引索值,用于选择对应页面的物理基地址。线性地址的低12位给出 了页面中的偏移量。页表中的页表项大小为32位。由于只需要其中20位来存放页面的物理基地址,因此剩下的12位可用于存放诸如页面是否存在等属性信息。如果线性地址引索的页表项被标注为存在,我们就从页面中取得物理地址。如果表项中不存在,那么访问对应物理页面时就会产生异常。

页表含有2^20(1M)个表项,而每项占用4个字节。如果作为一个表来存放的话,最多将占用4MB内存。因此为了减少内存占用量,80x86适用了两级表。由此,高20位线性地址到物理地址的转换也被分成两步进行,每部适用其中10个比特。

第一级表称为页目录。它被存放在1页4k 页面中,具有2^10(1k)个4字节长度的表项。这些表项指向二级表。它们由线性地址最高10位作为引索。

第二级表称为页表,长度也是1个页面。线性地址高10位获取指向第二级页表的指针,再加上中间10位,就可以在相应页表中获得物理地址的高20位。而为地址的低12位就是线性地址的低12,这样就组成了一个完整的32位物理地址。分段、分页的整个过程可见下面这张图:

以上就是良许教程网为各位朋友分享的Linux相关知识。

linux 运行可执行文件相关推荐

  1. Linux运行可执行文件

    原先以为linux下运行可执行文件在文件名前加"./"是执行命令,今天才搞明白是指当前目录 转载于:https://www.cnblogs.com/dpc525/archive/2 ...

  2. Linux下可执行文件指定运行时库(.so文件)路径

    rpath 全称是run-time search path,规定了Linux下可执行文件在寻找.so文件时的第一优先位置.比如我们想要指定可执行文件运行优先在当前目录下寻找.so 文件,则使用gcc/ ...

  3. GCC 链接 xxx:No such file or directory 及运行可执行文件 error while loading shared libraries: xxx.so 解决方案

    关于 GCC 提示找不到指定库文件的这个问题,通常出现在以下 2 个场景中: 利用静态库或者动态库文件实现链接操作(生成可执行文件)时,·GCC 可能会提示 xxx:No such file or d ...

  4. Linux执行可执行文件提示No such file or directory的解决方法

    Linux执行可执行文件提示No such file or directory的解决方法 查阅资料后,原因是系统位数与该可执行文件需要的lib库位数不匹配. 用uname命令打印系统信息,发现系统是6 ...

  5. Linux运行8086代码,* linux下编译,链接,运行,汇编程序

    当前使用的操作系统:ubuntu11.10 汇编程序由定义好的段构成,每个段都有不同的目的,三个最常用的段: 1)data 段 汇编程序data(数据)段是可选的. 数据段声明带有初始值的数据元素,这 ...

  6. Go Windows上生成适用于 Linux 的可执行文件

    阅读目录 Go Windows上生成适用于 Linux 的可执行文件 Go Windows上生成适用于 Linux 的可执行文件 在Windows上生成适用于Linux的可执行文件是一项相对复杂的任务 ...

  7. Linux生成可执行文件

    https://blog.csdn.net/a879365197/article/details/72933916 linux下c语言工程: c文件:主要每个模块的原代码都在c文件中. h文件:每个c ...

  8. UNIX/LINUX 平台可执行文件格式分析

    UNIX/LINUX 平台下三种主要的可执行文件格式:a.out(assembler and link editor output 汇编器和链接编辑器的输出).COFF(Common Object F ...

  9. linux 后台运行jar包命令,Linux 运行jar包命令(Cent OS 7后台运行jar包)

    Linux 运行jar包命令如下: 方式一 特点:当前ssh窗口被锁定,可按CTRL + C打断程序运行,或直接关闭窗口,程序退出 那如何让窗口不锁定? 方式二 java -jar shareniu. ...

  10. 使用 CrossOver 在 Linux运行 Windows 软件(金测OK)

    使用 CrossOver 在 Linux运行 Windows 软件 即便是最忠实的 Linux 用户,有时候也需要运行一下 Windows  软件.有的用户为此保留了一台旧的 Windows PC,有 ...

最新文章

  1. excel调用python编程-用Python如何开发Excel宏脚本?新手必学
  2. python 期货交易_Python期货量化交易基础教程(8)
  3. sudo apt install ...
  4. Java怎么重复使用套接字_在java中连续地通过套接字传输数据
  5. 软件设计原则(七)合成/聚合复用原则(Composite/Aggregate Reuse Principle,CARP)
  6. DotNetCommon-搜集.neter开发常用的功能
  7. net core 3.0 之Grpc新特性小试牛刀
  8. .net core 中间件管道底层剖析
  9. ListView执行notifyDatasetChanged无数据显示,getView未执行
  10. 【Siddhi】Siddhi 入门案例
  11. 软件开发过程回归与回溯之区别
  12. 面向临床需求的CT图像降噪综述
  13. win7系统如何映射服务器,教你win7系统映射网络驱动器的操作方法
  14. 2022年计算机二级Python考哪些内容?
  15. 用bmfont工具生成.fnt文件,但合成图片会分开问题
  16. Windows系统合并磁盘分区
  17. xss获取键盘记录实验演示
  18. 乱砍设计模式之三 -- DECORATOR模式
  19. javaMailSender 发送邮件设置昵称
  20. c语言程序设计教程中国农业出版社答案,C语言程序设计教程杨路明课后习题答案北京邮电大学出版社.pdf...

热门文章

  1. 关于jesd204出错
  2. AD9371+ZYNQ结构中JESD204B IP核的AXI_STREAM接口数据结构
  3. 记一次ARM CHINA面试
  4. SQLServer游标详解
  5. Linux操作系统之常用快捷键汇集
  6. SVN 回退到某一个版本
  7. pycharm连接SqlServer数据库
  8. 支付宝”向他付款”,定额付款收款链接生成
  9. 程序员软件工程常用的画图软件推荐
  10. apktool+dex2jar+xjad反编译APK文件