程序人生 HELLO‘s P2P

目  录

第1章 概述................................................................................... - 4 -

1.1 Hello简介............................................................................ - 4 -

1.2 环境与工具........................................................................... - 4 -

1.3 中间结果............................................................................... - 4 -

1.4 本章小结............................................................................... - 4 -

第2章 预处理............................................................................... - 5 -

2.1 预处理的概念与作用........................................................... - 5 -

2.2在Ubuntu下预处理的命令................................................ - 5 -

2.3 Hello的预处理结果解析.................................................... - 5 -

2.4 本章小结............................................................................... - 5 -

第3章 编译................................................................................... - 6 -

3.1 编译的概念与作用............................................................... - 6 -

3.2 在Ubuntu下编译的命令.................................................... - 6 -

3.3 Hello的编译结果解析........................................................ - 6 -

3.4 本章小结............................................................................... - 6 -

第4章 汇编................................................................................... - 7 -

4.1 汇编的概念与作用............................................................... - 7 -

4.2 在Ubuntu下汇编的命令.................................................... - 7 -

4.3 可重定位目标elf格式........................................................ - 7 -

4.4 Hello.o的结果解析............................................................. - 7 -

4.5 本章小结............................................................................... - 7 -

第5章 链接................................................................................... - 8 -

5.1 链接的概念与作用............................................................... - 8 -

5.2 在Ubuntu下链接的命令.................................................... - 8 -

5.3 可执行目标文件hello的格式........................................... - 8 -

5.4 hello的虚拟地址空间......................................................... - 8 -

5.5 链接的重定位过程分析....................................................... - 8 -

5.6 hello的执行流程................................................................. - 8 -

5.7 Hello的动态链接分析........................................................ - 8 -

5.8 本章小结............................................................................... - 9 -

第6章 hello进程管理.......................................................... - 10 -

6.1 进程的概念与作用............................................................. - 10 -

6.2 简述壳Shell-bash的作用与处理流程........................... - 10 -

6.3 Hello的fork进程创建过程............................................ - 10 -

6.4 Hello的execve过程........................................................ - 10 -

6.5 Hello的进程执行.............................................................. - 10 -

6.6 hello的异常与信号处理................................................... - 10 -

6.7本章小结.............................................................................. - 10 -

第7章 hello的存储管理...................................................... - 11 -

7.1 hello的存储器地址空间................................................... - 11 -

7.2 Intel逻辑地址到线性地址的变换-段式管理................... - 11 -

7.3 Hello的线性地址到物理地址的变换-页式管理............. - 11 -

7.4 TLB与四级页表支持下的VA到PA的变换.................... - 11 -

7.5 三级Cache支持下的物理内存访问................................ - 11 -

7.6 hello进程fork时的内存映射......................................... - 11 -

7.7 hello进程execve时的内存映射..................................... - 11 -

7.8 缺页故障与缺页中断处理................................................. - 11 -

7.9动态存储分配管理.............................................................. - 11 -

7.10本章小结............................................................................ - 12 -

第8章 hello的IO管理....................................................... - 13 -

8.1 Linux的IO设备管理方法................................................. - 13 -

8.2 简述Unix IO接口及其函数.............................................. - 13 -

8.3 printf的实现分析.............................................................. - 13 -

8.4 getchar的实现分析.......................................................... - 13 -

8.5本章小结.............................................................................. - 13 -

结论............................................................................................... - 14 -

附件............................................................................................... - 15 -

参考文献....................................................................................... - 16 -

第1章 概述

1.1 Hello简介

       关于hello的一生:就p2p而言,就是hello.c的源文件经过预处理,编译,汇编,链接,从.c,.i,.s,.o到可执行文件的过程。020指程序在内存中的创建直至回收。Shell调用fork,和execve以创建并加载进程,通过mmap开创空间。映射进虚拟内存,在相关位置取代码,数据。规划时间片,处理异常。最后程序结束时,父进程回收子进程,进行删除和回复。

1.2 环境与工具

软件环境:Windows7 64位以上;VirtualBox/Vmware 11以上;Ubuntu 16.04 LTS 64位/优麒麟 64位

硬件环境:X64 CPU;2GHz;2G RAM;256GHD Disk 以上

开发/调试工具:Visual Studio 2010 64位以上;CodeBlocks 64位;vi/vim/gedit+gcc

1.3 中间结果

令hello.i(预处理后文件),hello.s(汇编文件),hello.o(重定位文件),hello(可执行文件);hello.o的elf文件,hello的elf文件;hello.o的反汇编文件,hello的反汇编文件。

1.4 本章小结

  本章阐述了程序的两个方面p2p,020。告知了实验的环境和使用工具。给出了实验过程中的中间结果。

(第1章0.5分)

第2章 预处理

2.1 预处理的概念与作用

预处理经由预处理器对原始的c程序中的预处理指令进行的操作,预处理指令通常以#符号开头。预处理会对头文件操作,将头文件源码插入到目标文件。同时会对宏定义和常量作处理,替换为相应代码值。根据条件决定编译的代码,进行测试等工作。生成i文件。

2.2在Ubuntu下预处理的命令

gcc -E hello.c -o hello.i

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

2.3 Hello的预处理结果解析

         预处理结果图:

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

    可以看到预处理后生成了.i文件。.i文件中有大量的代码来自预处理步骤的对头文件的引入;并仍可观察到main函数代码。

2.4 本章小结

       本章说了预处理的相关,并实际操作了预处理步骤,观察到预处理结果。

(第2章0.5分)

第3章 编译

3.1 编译的概念与作用

      编译是由.i文件生成.s文件的过程。编译过程对语法和词法进行分析,将高级语言译为汇编语言。

3.2 在Ubuntu下编译的命令

       为gcc -S hello.i -o hello.s

正在上传…重新上传取消转存失败重新上传取消正在上传…重新上传取消

3.3 Hello的编译结果解析

3.3.1声明

.file 指明源文件名;

.text 代码段;

.section .rodata 只读数据段;

.align 地址对齐伪指令,指定对齐方式;

.string 声明字符串,后跟存储位置;

.global 全局声明;

.type类型声明;

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

3.3.2数据

串类型:

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

.s文件中的串位于只读数据段。

立即数:

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

加法中$16为立即数。

全局变量:

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

局部变量:

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

局部变量存储在栈中为-4(%rbp)的位置,局部变量可存储在存储器中。

3.3.3操作

函数调用:

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

汇编语言通过call命令进行函数调用。调用过程涉及到参数的传入和函数值的返回,这与栈的作用有关。

算数操作:

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

加减两种算数操作。

赋值操作:

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

两种赋值操作:1.move指令 和 2.lea指令。

3.3.4结构

数组:

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

栈中的一段连续的空间开辟为数组存储,以类似指针的操作方式进行数组单元的操作。

3.3.5转移关系

条件跳转:

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消除条件跳转外,还有无条件跳转。

循环:

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

通过赋值操作和条件跳转对循环的一种实现。

3.3.6判断

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

Cmpl指令比较,通常用于判断。

3.4 本章小结

       本章是对编译过程的实验。实验就编译的生成文件分析。结合的是汇编语言的相关内容,就汇编相关的操作进行了大致的概括。

(第32分)

第4章 汇编

4.1 汇编的概念与作用

       汇编是由汇编或中间语言生成机器语言,从.s文件到.o文件的过程。汇编将指令打包为一种可重新定位的格式保存在.o文件中,是一个二进制文件。

4.2 在Ubuntu下汇编的命令

gcc -c hello.s -o hello.o

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

4.3 可重定位目标elf格式

通过readelf -a hello.o >hell_o.elf生成elf文件。

Elf文件由elf头,节头,字母表和重定位节构成。由典型的节格式,具体为

ELF

.text

.rodata

.data

.bss

.symtab

.rel.text

.rel.data

.debug

.line

.strtab

节头部

ELF头以一个16字节开始,描述了生成该文件的系统的字大小和字节顺序,ELF头剩下的部分包含帮助其语法分析和解释目标文件的信息,包括ELF头的大小、目标文件的类型、机器类型、节头部表的文件偏移以及节头部表中条目的大小和数量等

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

重定位节是其中的.rel.text,rel.data部分。rel.textc存储.text节的重定位信息,用于重新修改代码段的指令中的地址信息。.rel.data存储.data节的重定位信息,用于对被模块使用或定义的全局变量重定位的信息。

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

节头,节头表负责记录各节名称、类型、地址、偏移量、大小、全体大小、旗标、链接、信息、对齐等信息。

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

符号表。.symtab.debug.strtab均为符号表的部分。用以存放符号信息。其中.symtab存放函数和全局变量信息。.debug存放调试信息。.strtab存放字符串信息。

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

4.4 Hello.o的结果解析

反汇编objdump -d hello.o > hello_o.txt 

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

比较:

反汇编中的立即数为16进制,为机器语言操作数格式,而在.s文件中是10进制的。在分支转移和函数调用方面。分支转移由跳转到标识位L映射为跳转到具体的确定地址。函数调用由模糊的函数名映射为具体的函数地址。

4.5 本章小结

本章就程序的汇编实验。实验给出了hello.o文件,其elf文件。对elf文件进行了具体的分析,明确各部分的作用。对hello.o文件反汇编,并与之.s文件比较。体现从.s到.o文件的变化。

(第41分)

5章 链接

5.1 链接的概念与作用

链接是将各种代码和数据片段收集并组合成为一个单一文件的过程,这个文件可以被加载到内存并执行。

链接使得程序可以模块化,使大的程序可以由小的程序组合构造生成。利于程序的管理。

5.2 在Ubuntu下链接的命令

       用指令链接:

ld -dynamic-linker /lib64/ld-linux-x86-64.so.2 /usr/lib/x86_64-linux-gnu/crt1.o /usr/lib/x86_64-linux-gnu/crti.o /usr/lib/gcc/x86_64-linux-gnu/11/crtbegin.o hello.o -lc /usr/lib/gcc/x86_64-linux-gnu/11/crtend.o /usr/lib/x86_64-linux-gnu/crtn.o -z relro -o hello

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

5.3 可执行目标文件hello的格式

命令readelf -a hello > hello.elf生成hello的elf文件。

查看hello.elf文件的Elf头

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

发现类型为EXEC可执行文件,节头长为30。字段entry point给出执行程序时的第一条指令的地址.而重定位文件中,此字段空。

查看节头

节头表中显示有, Size大小, Offset偏移量,Address被载入虚址地址的起始地址。

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

查看符号表

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

查看程序头

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

程序头表是一个结构数组,给出虚拟地址,物理地址,映射关系,对齐,权限等信息。

查看.init段

.init段定义init函数执行可执行目标文件开始执行时的初始化工作。

可执行文件不需要重定位,没有重定位节。

5.4 hello的虚拟地址空间

通过查看。Elf文件内容。在各节progbits处找到对应的起始地址

虚拟空间的起始地址:0x400000

    正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

又.rodata的起始地址:0x420000

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

5.5 链接的重定位过程分析

objdump -d hello > hello.txt 生成hello的反汇编文件。

Hello的反汇编文件较hello.o的除main外多出很多节:

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

而main节几乎无有变化:

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

.o文件的main:

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

但确定了虚拟地址替代.o文件中的偏移量。

新生成的部分:

新生成部分是对程序执行过程中的数据的保存和操作的支持相关的。

.interp 保存ld.so的路径

.note.ABI.tag Linux下特有的section

.note.gnu.build-i 编译信息表

.gnu.hash gnu的扩展符号hash表

.dynsym 动态符号表

.dynstr 动态符号表中的符号名称

.gnu.version 符号版本

.gnu.version_r 符号引用版本

.rela.dyn 动态重定位表

.rela.plt .plt节的重定位条目

.init 初始化函数

.plt 动态链接表

.fini 程序终止时需要的执行的指令

.eh_frame 程序执行错误时的指令

.dynamic 存放被ld.so使用的动态链接信息

.got 存放程序中变量全局偏移量

.got.plt 存放程序中函数的全局偏移量

.data 初始化过的全局变量或者声明过的函数

重定位过程

      重定位通过符号表确定定位的主体。链接器在完成符号解析以后,就把代码中的每个符号引用和一个符号定义关联起来。合并输入模块为同一类型的新节,并为每个符号分配运行时的地址。采用对应的寻址方式,对偏移量分析,明确为具体的地址。直接进行跳转。

5.6 hello的执行流程

Edb查看内容如下:

hello!_start   0x00000000004010f0

hello!__libc_csu_init 0x0000000000401270

hello!_init    0x0000000000401000

hello!frame_dummy  0x00000000004011d0

hello!register_tm_clones  0x0000000000401160

hello!main   0x00000000004011d6

hello!printf@plt  0x0000000000401040

hello!atoi@plt    0x0000000000401060

hello!sleep@plt  0x0000000000401080

hello!getchar@plt      0x0000000000401050

hello!exit@plt    0x0000000000401070

hello!__do_global_dtors_aux  0x00000000004011a0

hello!deregister_tm_clones     0x0000000000401130

hello!_fini    0x00000000004012e8

5.7 Hello的动态链接分析

              动态链接采用执行时加载的延迟绑定技术。与got段和plt段相关。

   在elf文件中找。.got

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

地址为0x403ff0

在dl_init前,edb相应值为:

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

dl_init后改变为:

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

5.8 本章小结

本章就程序的链接过程进行了详尽的分析。从生成,elf文件,反汇编文件出法,具体到重定位过程,加载运行时的调用至动态链接。细致地阐述了链接在程序中的过程。

(第51分)

6章 hello进程管理

6.1 进程的概念与作用

进程是一个执行中程序的实例。是系统进行资源分配和调度的基本单位,是操作系统结构的基础。

进程是对程序的一次细分。让程序可以对由内部程的变化做出反应。

6.2 简述壳Shell-bash的作用与处理流程

Shell是一个应用程序,它链接了用户和Linux内核,让用户能更加高效、安全、低成本地使用Linux内核。Shell是一种命令行的操作,它会读取命令行命令,解析读取的命令,最后执行它。

处理流程:

  1. 读取键入的命令行
  2. 分析命令行,获取参数,构造传递给execveargv指针
  3. 检查命令是否内置
  4. 不然则调用fork创建子进程
  5. 在子进程中调用execve执行
  6. 父进程回收子进程
  7. Shell返回

6.3 Hello的fork进程创建过程

当输入非内置命令时,shell会用fork创建子进程来执行键入的命令。子进程几乎但不完全与父进程相同,具有不同的PIDFork调用1次,执行两次。进程并行执行。通过返回值区分父子进程。

6.4 Hello的execve过程

Execve会在当前进程加载并运行一个附带参数列表和环境变量列表的新程序。完成删除已有用户空间,开辟代码、数据段、堆、共享库以及用户栈,构建区域映射等一系列操作。Execve调用但不返回。只错误返回。

6.5 Hello的进程执行

控制流:处理器将同时运行中的进程分成不同的逻辑流,他们的执行是交错的,每个进程执行其流的一部分。

上下文:内核重新启动一个被抢占的进程所需要恢复的原来的状态,启前,启后构成一个上下文。

内核模式:处于故障、中断或是系统调用时的一种操作权限更高的一种模式。作为一种保护机制,只有在故障、中断或是系统调用时切换。

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

6.6 hello的异常与信号处理

异常:

中断 来自I/O设备的信号 异步 总是返回到下一条指令
陷阱 有意的异常 同步 总是返回到下一条指令
故障 潜在可恢复的错误 同步 可能返回到当前指令或终止
终止 不可恢复的错误 同步 不会返回

乱按,回车:

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

打印到终端上,程序不停。

Ctrl c:结束进程

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

Ctrl z:挂起

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

Ps命令查看状态:

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

Fg恢复挂起进程:

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

Kill杀死进程:

正在上传…重新上传取消正在上传…重新上传取消正在上传…重新上传取消

6.7本章小结

本章是进程的执行过程。探讨了进程的由来,shell,两个关键fork 和 execve。

并由具体程序操作了异常的相关。

(第61分)

7章 hello的存储管理

7.1 hello的存储器地址空间

逻辑地址:逻辑地址用来指定一个操作数或者是一条指令的地址,是由一个段标识符加上一个指定段内相对地址的偏移量。

线性地址:逻辑地址经过段机制后转化为线性地址。

虚拟地址:保护模式下程序访问存储器所用的逻辑地址。

物理地址:加载到内存地址寄存器中的地址,内存单元的真正地址。CPU对内存的访问是通过连接着CPU和北桥芯片的前端总线来完成的。在前端总线上传输的内存地址都是物理内存地址。

7.2 Intel逻辑地址到线性地址的变换-段式管理

段式管理涉及到段标识符,索引号,段描述符表和Base字段。

段标识符是段内偏移量由一个16位长的字段组成,称段选择符。

13位即是索引号,索引号是段描述符的索引,段描述符具体地描述了一个段。

多个段描述符,组成的数组,叫段描述符表

Base字段描述了一个段的开始位置的线性地址。

对一个给定的逻辑地址通过段式管理的方式变换到一个线性地址。先根据段选择符判断要转换是全局段描述符表中的段还是局部段描述符表中的段。其中,T1字段,=0表示用全局段描述符表,=1表示用局部段描述符表。再者根据段选择符前13位查找到段描述符,确定Base基址。得出线性地址为Base+offset

7.3 Hello的线性地址到物理地址的变换-页式管理

线性地址到物理地址分页完成。

从线性地址到物理地址为提高访问速度采用虚拟页进行管理,在页表中查询地址是否在缓存中。一条虚拟地址可分为虚拟页号和虚拟页偏移量。Cpu由虚拟页号确定页表条目,有效位为1时,在页表中取出物理页号,根据虚拟页偏移量得到物理偏移量,组合为物理地址。为提高效率,进一步提供页表的缓存,tlb。在查询时先在tlb中查询,不命中则在页表查询,页表亦不命中则按缺页处理。

7.4 TLB与四级页表支持下的VA到PA的变换

Core i7采用四级页表的层次结构。CPU产生VA,VA传送给MMU,MMU使用VPN高位作为TLBT和TLBI向TLB中寻找匹配。如果命中,则得到PA。如果TLB中没有命中,MMU查询页表,CR3确定第一级页表的起始地址,VPN1确定在第一级页表中的偏移量,查询出PTE,以此类推,最终在第四级页表中找到PPN,与VPO组合成PA,添加到PLT。

7.5 三级Cache支持下的物理内存访问

在Cache支持下内存访问有以下步骤:

组选择:取出虚拟地址的组索引,找到相应的组进行匹配:把虚拟地址的标记位拿与相应的组中所有行的标记位比较,当虚拟地址的标记位和高速缓存行的标记位匹配时,且有效位为1,则高速缓存命中。

字选择:一旦高速缓存命中,我们就知道我们要找的字节在这个块的某个地方。因此块偏移位提供了第一个字节的偏移。把这个字节的内容取出返回给CPU。如果高速缓存不命中,那么需要从存储层次结构中的下一层取出被请求的块,然后将新的块存储在组索引位所指示的组中的一个高速缓存行中。

7.6 hello进程fork时的内存映射

当fork函数被当前进程调用时,内核为新进程创建各种数据结构,并分配给它一个唯一的PID,同时为这个新进程创建虚拟内存。

它创建了当前进程的mm_struct、区域结构和页表的原样副本。它将两个进程中的每个页面都标记位只读,并将两个进程中的每个区域结构都标记为私有的写时复制。

当fork在新进程中返回时,新进程现在的虚拟内存刚好和调用fork时存在的虚拟内存相同。当这两个进程中的任一个后来进行写操作时,写时复制机制就会创建新页面。因此,也就为每个进程保持了私有空间地址的抽象概念

7.7 hello进程execve时的内存映射

运行execve过程如下:

首先,删除已存在的用户区域。其次,映射私有区域,为新程序的代码、数据、bss和栈区域创建新的区域结构。而后,对共享区域的映射。最后,设置程序计数器,指向代码区域的入口点。

7.8 缺页故障与缺页中断处理

在访存时如果缺页,就会造成缺页故障。对缺页故障采用中断处理的方式。

对造成缺页的指令进程进行中断。设法排除指令故障,如通过从外存加载该页的方法来排除故障,重启指令继续执行。缺页中断的处理函数具体为do_page_fault函数,进行一般的中断操作。

7.9动态存储分配管理

动态内存分配器维护着堆,进程的一个虚拟内存区域。分配器将堆视为一组不同大小的块的集合来维护。每个块就是一个连续的虚拟内存片,要么是已分配的,要么是空闲的。已分配的块显式地保留为供应用程序使用。空闲块可用来分配。空闲块保持空闲,直到它显式地被应用所分配。一个已分配的块保持已分配状态,直到它被释放,这种释放要么是应用程序显式执行的,要么是内存分配器自身隐式执行的。

分配器可被分为显式分配器、隐式分配器。

显式分配器显式地分配内存,通常是对主体需要的回应。

隐式分配器隐式地分配内存,作回收工作,客观处理已分配的不在使用的块。

动态管理涉及分配,相应,回收,维护,合并,申请等操作,在内存管理上占有重要的地位。

7.10本章小结

本章在存储上作文章,涉及四种地址类别。地址管理方式。到内存管理,Cache,动态分配。分析了缺页故障的中断保护,forkexecve函数的内存映射机制。

(第7 2分)

8章 hello的IO管理

8.1 Linux的IO设备管理方法

设备的模型化:所有的I/O设备都被模型化为文件,输入和输出都被当做对相应文件的读和写来执行

设备管理:unix io接口方式允许Linux内核弹出名为Unix I/O的一个简单、低级应用接口。从而使文件执行时得到统一。

8.2 简述Unix IO接口及其函数

Unix I/O接口已存在在上述内容中。下面简述一些Unix I/O函数:

  1. open()打开方式,用于打开或创建一个文件,参数为路径名,可以指定打开的文件权限,失败返回-1
  2. read()write()读写文件,返回所读,所写的字节数,失败返回-1
  3. close()关闭文件,成功返回0,失败返回-1
  4. lseek()移动读写头至指定位置,参数为文件描述符,移动偏移量。失败返回-1

8.3 printf的实现分析

在程序中执行到printf()语句时,程序转到I/O标准库去执行。

在vsprintf处生成显示信息,经过一系列调用到write系统函数。

通过一系列步骤到陷阱-系统进入内核空间调用服务例程sys_write去执行。

从ASCII到字模库到显示vram(存储每一个点的RGB颜色信息)。

显示芯片按照刷新频率逐行读取vram,并通过信号线向液晶显示器传输每一个点(RGB分量)。

8.4 getchar的实现分析

Getchar实现时采用中断模式。在接受按键转成ascii码,保存到系统的键盘缓冲区。

getchar调用read系统函数从缓冲区读行,直到接受到回车键才返回且只返回第一个字符。对于不止一个字符的输入,中断模式保证了除第一个字符外的其余字符保存在缓冲区。再调用getchar时无论输入何为,读取的是缓冲区的第一个字符。

8.5本章小结

本章介绍了LinuIO设备管理方法Unix IO接口及其函数。分析了printf函数和getchar函数的实现。

(第81分)

结论

本次的实验内容从hello程序的一生出发,详细地对计算机系统这门课程所学的内容做出了阐释。无论是预处理过程的引入,编译和反汇编生成的汇编语言,还是中断过程的峰形处理。从内存到I/O,从shell到命令行。方方面面,全身心的,无不是让人深感动容的计算机魅力。学习计算思维时,战德臣老师曾经说他的这门课会让你受用一生。它又何尝不是呢?从hello的一生来看,其实是人的一生,从.c开始的那一个1,到执行结束的进程回收。那便是hello的生与死。Hello是从020的,但过程中它偏偏的实现了自己预定的价值,活出了精彩。我深深的记得的是这样的一句话:人生的价值,不在于其长度,而在于其宽度,不是得到了什么,而是为他人,为这个社会奉献了什么。实验结束,感慨良多,虽空谈无意,但寥寥数语,与君等共勉。

附件

中间产物:

hello.c  源程序

hello.i   hello.c预处理得到的预处理文件

hello.s  hello.i编译得到的汇编文件

hello.o  hello.s汇编之后的重定位文件

hello  hello可执行文件

hello_o.elf  hello.o的elf文件

hello.elf  hello的elf文件

hello_o.txt  hello.o的反汇编文本文件

hello.txt  hello的反汇编文本文件

(附件0分,缺失 -1分)

参考文献

为完成本次大作业你翻阅的书籍与网站等

[1]  深入理解计算机系统3版,出版物

[2]  Linux id 命令 | 菜鸟教程 (runoob.com)

[3]  https://www.cnblogs.com/pianist/p/3315801.html

[4]  Shell简介:Bash的功能与解释过程(一) Shell简介 - 知乎 (zhihu.com)

(参考文献0分,缺失 -1分)

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 2
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值