2019-2020-1 20199327《Linux内核原理与分析》第二周作业 计算机工作原理

1.冯诺依曼体系结构

五大组件:运算器、存储器、控制器、输入与输出设备
核心思想:存储程序;
计算机内部采用二进制来表示指令和数据。

2.汇编基础

CPU通用寄存器

 数据寄存器
AX:累加寄存器
BX:基地址寄存器
CX:计数器寄存器
DX:数据寄存器
指针寄存器
SP:堆栈指针寄存器
BP:基指针寄存器
 变址寄存器
SI:源变址寄存器
DI:目的变址寄存器

其他寄存器

标志寄存器、指令寄存器、段寄存器

寄存器位数分辨

E:32位;R:64位;
在定位一个指令时,使用CS:EIP来准确指明他的地址。

寻址方式

三种操作数

立即数: 常数,符号$加数值;
寄存器数: 寄存器中保存的值,%eax;对字节操作是对八个单字节寄存器的一个,%al;
寄存器引用:经过计算的有效地址访问;

寻址方式

寄存器寻址:movl %eax,%eax;  edx=edx;
立即寻址:movl $0x123,%eax;  edx=0xedx;
直接寻址:movl 0x123,%eax     edx=*(int*)0xedx;
间接寻址:movl (%eax),%eax;  edx=*(int*)edx
变址寻址:movl 4(%eax),%eax; edx=*(int*)(edx+4)

常用指令

pushl: 压栈 指令:pushl %eax;
执行步骤1.subl $4, %esp;
执行步骤2.movl %eax,(%eap);
popl:出栈 指令:popl %eax;
执行步骤1.movl (%esp),%eax;
执行步骤2.addl $4, %esp;
call:函数调用 指令:call 0x12345;
pushl %eip
movl $0x123245, %eip
两个动作一次完成
ret:函数返回 指令:ret;
popl %eip

实验

编译过程:预处理 编译 汇编 链接
 1     int g(int x)
 2     {
 3         return x + 5;
 4     }
 5     int f(int x)
 6     {
 7         return g(x);
 8     }
 9      int main(void)
10     {
11        return f(8) + 1;
12     }

main.c文件中内容。经gcc -S -o main.s main.c -m32将其转化为汇编语言 

 1 .file "main.c"
 2  .text
 3  .globl g
 4  .type g, @function
 5 g:
 6 .LFB0:
 7  .cfi_startproc
 8  pushl %ebp
 9  .cfi_def_cfa_offset 8
10  .cfi_offset 5, -8
11  movl %esp, %ebp
12  .cfi_def_cfa_register 5
13  movl 8(%ebp), %eax
14  addl $5, %eax
15  popl %ebp
16  .cfi_restore 5
17  .cfi_def_cfa 4, 4
18  ret
19  .cfi_endproc
20 .LFE0:
21  .size g, .-g
22  .globl f
23  .type f, @function
24 f:
25 .LFB1:
26  .cfi_startproc
27  pushl %ebp
28  .cfi_def_cfa_offset 8
29  .cfi_offset 5, -8
30  movl %esp, %ebp
31  .cfi_def_cfa_register 5
32  subl $4, %esp
33  movl 8(%ebp), %eax
34  movl %eax, (%esp)
35  call g
36  leave
37  .cfi_restore 5
38  .cfi_def_cfa 4, 4
39  ret
40  .cfi_endproc
41 .LFE1:
42  .size f, .-f
43  .globl main
44  .type main, @function
45 main:
46 .LFB2:
47  .cfi_startproc
48  pushl %ebp
49  .cfi_def_cfa_offset 8
50  .cfi_offset 5, -8
51  movl %esp, %ebp
52  .cfi_def_cfa_register 5
53  subl $4, %esp
54  movl $8, (%esp)
55  call f
56  addl $1, %eax
57  leave
58  .cfi_restore 5
59  .cfi_def_cfa 4, 4
60  ret
61  .cfi_endproc
62 .LFE2:
63  .size main, .-main
64  .ident "GCC: (Ubuntu 4.8.2-19ubuntu1) 4.8.2"
65  .section .note.GNU-stack,"",@progbits

 

上述为main.s中内容。
gcc中常用选项: 1. -o <FILE> 指定输出的文件,如果是一个文件的C程序不指定-o选项,则输出的文件是一个a.out的可执行文件,运行。./a.out运行
 2. -c 只编译不连接,通知GCC取消链接步骤,即编译源码并在最后生成目标文件
 3. -I 指定include搜索的路径。
 4. -L 指定库的搜索路径。
 5.  -l 指定所用到的库。
 6. -g 加入调试信息。
 7. -o与-g不能联用。