源码下载
Linux 源码下载路径位于 https://mirrors.edge.kernel.org/pub/linux/kernel/,这篇博客所需要的 0.10 版本源码通过点击链接 https://mirrors.edge.kernel.org/pub/linux/kernel/Historic/old-versions/tytso/linux-0.10.tar.gz 可下载,由于 Linux 0.10 版本由 Theodore Yue Tak Ts’o 发布的,所以 linux 0.10 版本在 tytso 目录下:
对比 Linux 0.01 版本 变化
Linux 0.10 对比 0.01 版本变化并不大,管理方法没有什么大的变化,也没有什么质的变化,主要是内存大小方面的小变化。
在 Linux 0.10 版本定义的可用内存范围增大了:
init/main.c
/*
* This is set up by the setup-routine at boot-time
*/
#define EXT_MEM_K (*(unsigned short *)0x90002)
void main(void) /* This really IS void, no error here. */
{ /* The startup routine assumes (well, ...) this */
/*
* Interrupts are still disabled. Do necessary setups, then
* enable them
*/
...
memory_end = (1<<20) + (EXT_MEM_K<<10);
memory_end &= 0xfffff000;
if (memory_end > 16*1024*1024)
memory_end = 16*1024*1024;
if (memory_end > 6*1024*1024)
buffer_memory_end = 2*1024*1024;
else
buffer_memory_end = 1*1024*1024;
mem_init(buffer_memory_end,memory_end);
...
}
在 boot/setup.s
程序中,它利用了 ROM BIOS 中断读取系统数据,并将这些数据保存在 0x90000
开始的地方,覆盖掉了 bootsect 程序的位置,其中 0x90002
存放的是系统从 1MB 开始的扩展数值,长度为 2 个字节,单位为 KB。Linux 0.10 版本最多管理 16 MB 内存,所以即使大于 16MB,也不会被使用。如果内存大于 6MB,定义缓冲区末端为 2MB,因此主内存区从 2MB 开始,如果不大于 6MB,那么缓冲区末端则为 1MB,则主内存区从 1MB 开始,总的来说,buffer_memory_end
,也就是缓冲区末端,定义了主内存区的起始地址,也就是 Linux 0.01 版本中的 LOW_MEM
。由于它最多 16MB 内存有意义,那我们就按系统有 16MB 内存就好了。接着调用 mem_init
函数初始化 mem_map
数组,记下传入 mem_init
的两个参数,表示主内存区的最低地址和最高地址+1。在这里要注意的是,Linux 0.10 版本中的 LOW_MEM
的含义和 0.01 版本的不一样,0.01 版本的 LOW_MEM
定义了主内存区的起始地址,而在 0.10 版本中,LOW_MEM
的定义如下:
mm/memory.c
#define LOW_MEM 0x100000
即定义为 1MB 处。不过从 mem_map
的角度看,LOW_MEM
的定义是一致的,都是 mem_map
数组管理的内存范围的起始地址:
mm/memory.c
#define PAGING_MEMORY (15*1024*1024)
#define PAGING_PAGES (PAGING_MEMORY>>12)
#define MAP_NR(addr) (((addr)-LOW_MEM)>>12)
#define USED 100
static unsigned char mem_map [ PAGING_PAGES ] = {0,};
0.01 版本 mem_map
:
static unsigned short mem_map [ PAGING_PAGES ] = {0,};
可见,0.10 版本对这些细节还是优化了的。
注意,0.10 版本中的 PAGING_MEMORY
直接定义为了 15MB,还定义了一个 USED
宏,在 mem_init
函数中将 LOW_MEM
到 buffer_memory_end
的区域置为 USED
,buffer_memory_end
到 memory_end
置为 0:
mm/memory.c
static long HIGH_MEMORY = 0;
void mem_init(long start_mem, long end_mem)
{
int i;
HIGH_MEMORY = end_mem;
for (i=0 ; i<PAGING_PAGES ; i++)
mem_map[i] = USED;
i = MAP_NR(start_mem);
end_mem -= start_mem;
end_mem >>= 12;
while (end_mem-->0)
mem_map[i++]=0;
}
mem_init
先将所有区域都置为 USED
,然后再将主内存区置为 0,这里应该可以优化,直接将 LOW_MEM
到 start_mem
置为 100,再将 start_mem
到 end_mem
置为 0。