在学习虚拟地址空间之前首先要了解这几个概念
变量:有名字的空间 用来存储数据
内存地址:内存区域的编号
1 #include <stdio.h>
2 #include <unistd.h>
3 #include <stdlib.h>
4
5 int val = 100;
6 int main()
7
8 {
9
10 pid_t pid = fork();
11 if(0 == pid)
12 {
13 val = 200;
14 printf("this is child: %d val = %d %p \n", pid, val,&val);
15
16 }
17 else if( pid > 0 )
18 {
19 sleep(2);
20 printf("this is parent: %d val = %d %p\n", pid, val, &val);
21
22
23 }
24 return 0;
25 }
~
在程序中全局变量在父子进程中的数据是不同的,一块空间只能存储一个数据,那么这表明父子进程中val变量用的不是空一块空间,但是我们在运行程序后结果却是这样的
内存地址是相同的,但是数据却是不同的,这是为什么?
实际上我们在进程中看到的地址都是虚拟地址,并不是物理内存的单位编号,我们所说的程序空间地址其实就是一个虚拟空间地址,所以这就可以做到两个相同的虚拟地址空间指向不同的物理内存地址。
虚拟地址空间是什么?
虚拟地址空间实际上是操作系统给进程描述的一个虚假的地址空间,通过虚拟地址空间给进程造成一个假象:我要一个连续的,完整的内存使用
为什么使用虚拟地址空间:
若进程直接访问物理内存:程序若使用连续物理地址空间,则会造成大量的内存碎片,对内存的利用率太低了,安全率低
鉴于这些原因,通过使用虚拟地址空间,不让进程不直接访问物理内存
使用虚拟地址向进程提供一个连续的,完整的地址使用,通过页表映射到物理内存的各个区域,这些物理区域可以不用连续,这样就实现了数据在物理内存上的离散式存储,提高了物理内存的利用率,并且虚拟地址空间可以对其中的地址进行访问控制,大大提高了内存访问的安全性。