哈工大计算机系统大作业--hello的一生
需积分: 0 41 浏览量
更新于2022-05-20
收藏 2.82MB DOCX 举报
### 哈工大计算机系统大作业--hello的一生
#### 概述
本文档深入探讨了一个简单的`hello`程序从编写至运行的全过程。这一旅程不仅涉及代码层面的转变,还包括程序如何被加载到内存中执行的具体细节。通过本项目,我们可以更深入地了解计算机系统的工作原理。
#### Hello简介
`Hello`程序起始于一个简单的C语言源文件`hello.c`。此文件包含了`main`函数,用于输出“Hello World!”。整个生命周期可分为几个关键阶段:预处理、编译、汇编、链接,最终形成一个可执行程序。
#### 环境与工具
- **操作系统**:Ubuntu
- **开发工具**:
- 预处理器:cpp
- 编译器:gcc
- 汇编器:as
- 链接器:ld
#### 中间结果
- **预处理**:生成`hello.i`文件,该文件包含所有宏定义和头文件的实际内容。
- **编译**:从`hello.i`生成`hello.s`,这是一个汇编语言程序。
- **汇编**:将`hello.s`转化为二进制格式的`hello.o`,即目标文件。
- **链接**:将`hello.o`与其他库文件链接,生成最终的可执行文件`hello`。
#### 预处理
**预处理的概念与作用**:预处理是编译前的一步,主要负责宏定义的展开、条件编译的处理、头文件的包含等操作。这一步是为了让编译器能更好地理解代码结构。
**预处理命令**:在Ubuntu下,可以通过`cpp`命令对源文件进行预处理。
**Hello的预处理结果解析**:预处理后的`hello.i`文件将不再包含任何宏定义或者条件编译指令,所有的`#include`语句都已经被替换为实际的文件内容。
#### 编译
**编译的概念与作用**:编译器将高级语言(如C)翻译成汇编语言。这一过程涉及到词法分析、语法分析、语义分析及代码优化等。
**编译命令**:在Ubuntu下,通常使用`gcc -S hello.c`来进行编译,生成`.s`文件。
**Hello的编译结果解析**:`hello.s`文件包含了一条条汇编指令,这些指令与源代码中的高级语言语句一一对应。
#### 汇编
**汇编的概念与作用**:汇编器将汇编语言转换为机器码,生成可重定位的目标文件。
**汇编命令**:使用`gcc -c hello.s`命令生成`hello.o`。
**可重定位目标elf格式**:`hello.o`遵循ELF格式标准,其中包含未解决的符号引用,需要通过链接器进行重定位。
**Hello.o的结果解析**:`hello.o`是一个二进制文件,包含汇编后的指令和数据段,以及符号表和重定位信息。
#### 链接
**链接的概念与作用**:链接器将多个目标文件和库文件组合起来,生成一个可执行文件。
**链接命令**:通过`gcc -o hello hello.o`完成链接过程。
**可执行目标文件hello的格式**:生成的`hello`是一个ELF可执行文件,包含了所有必要的信息以便于操作系统加载和执行。
**hello的虚拟地址空间**:程序运行时,操作系统会为它分配一个虚拟地址空间,包括代码段、数据段、栈段和堆段等。
**链接的重定位过程分析**:链接器根据符号表和重定位信息修改目标文件中的地址,确保所有依赖正确地加载到内存中。
**hello的执行流程**:
1. 当用户在shell中键入`./hello`命令时,shell通过fork和execve系统调用来启动程序。
2. 操作系统将`hello`程序加载到内存中,并初始化进程的上下文。
3. `hello`程序执行`main`函数,输出“Hello World!”。
**Hello的动态链接分析**:对于使用动态链接的程序,链接器会在运行时解析未解决的符号引用,确保所有依赖正确加载。
#### 进程管理
**进程的概念与作用**:进程是操作系统资源分配的基本单位,包含了程序执行所需的全部状态信息。
**Shell-bash的作用与处理流程**:shell是用户的命令行界面,它接收用户输入的命令并通过fork和execve创建并启动新的进程。
**Hello的fork进程创建过程**:fork函数创建一个新的进程副本,具有与父进程相同的资源和状态。
**Hello的execve过程**:execve系统调用用于替换当前进程的映像,加载并执行新的程序。
**Hello的进程执行**:`hello`程序在独立的进程中运行,直到正常结束或出现异常而终止。
**hello的异常与信号处理**:程序执行过程中可能会遇到各种异常情况,如除零错误或内存访问错误,这些异常通过信号传递给操作系统处理。
#### 存储管理
**hello的存储器地址空间**:每个进程都有自己的虚拟地址空间,包括代码段、数据段、栈段和堆段等。
**Intel逻辑地址到线性地址的变换-段式管理**:在x86架构中,逻辑地址通过段寄存器和偏移量组合而成,经过段式管理器转换为线性地址。
**Hello的线性地址到物理地址的变换-页式管理**:线性地址进一步通过页表转换为物理地址。
**TLB与四级页表支持下的VA到PA的变换**:快表(Translation Lookaside Buffer, TLB)用于加速虚拟地址到物理地址的转换。
**三级Cache支持下的物理内存访问**:CPU访问内存时首先尝试从高速缓存中读取数据,以此提高数据访问速度。
**hello进程fork时的内存映射**:在创建子进程时,父进程的内存空间被复制给子进程,但它们共享相同的物理页面,直到某个进程修改了内存内容触发写时复制机制。
**hello进程execve时的内存映射**:当进程执行`execve`调用时,其内存映像会被新程序替换,包括代码段和数据段。
**缺页故障与缺页中断处理**:当CPU尝试访问不在物理内存中的页面时,会产生缺页故障,操作系统需要处理此中断并将所需页面从磁盘加载到内存中。
**动态存储分配管理**:程序运行期间可能需要动态分配和释放内存,通过malloc和free等函数进行管理。
#### IO管理
**Linux的IO设备管理方法**:Linux通过文件描述符来抽象各种设备,使得对设备的操作统一为文件操作。
**UnixIO接口及其函数**:提供了read、write、open、close等函数,用于读写文件和设备。
**printf的实现分析**:`printf`函数内部使用`write`系统调用来向标准输出发送格式化字符串。
**getchar的实现分析**:`getchar`函数用于从标准输入读取字符,底层调用了`read`系统调用来获取数据。
#### 结论
通过本次大作业,我们深入了解了`hello`程序从源代码到可执行文件再到实际运行的全过程。这一过程涵盖了预处理、编译、汇编、链接等多个环节,同时也涉及了进程管理、存储管理和I/O管理等方面。这一系列步骤共同协作,使得一个简单的“Hello World!”程序得以顺利运行。
#### 附件
- `hello.c`源代码
- 各阶段产生的文件(`hello.i`, `hello.s`, `hello.o`)
- 可执行文件`hello`
#### 参考文献
- [1] Tanenbaum, A.S., Woodhull, A.S. (2006). "Operating Systems: Design and Implementation", 3rd Edition.
- [2] Stallings, W. (2010). "Operating Systems: Internals and Design Principles", 7th Edition.
- [3] Kernighan, B.W., Ritchie, D.M. (1988). "The C Programming Language", 2nd Edition.
Mr.9661
- 粉丝: 1
- 资源: 1
最新资源
- 面部、耳廓损伤损伤程度分级表.docx
- 农资使用情况调查问卷.docx
- 燃气管道施工资质和特种设备安装改造维修委托函.docx
- 食物有毒的鉴定方法.docx
- 市政道路工程联合质量抽检记录表.docx
- 市政道路工程联合质量抽检项目、判定标准、频率或点数.docx
- 视力听力残疾标准.docx
- 视器视力损伤程度分级表.docx
- 收回扣检查报告.docx
- 输液室管理制度、治疗配药室、注射室、处置室感染管理制度、查对制度.docx
- 听器听力损伤程度分级表.docx
- 新生儿评分apgar标准五项、五项体征的打分标准.docx
- 医疗废弃物环境风险评价依据、环境风险分析.docx
- 预防溺水宣传口号.docx
- 招标代理方案评分表.docx
- 职业暴露后的处理流程.docx