- 论坛徽章:
- 0
|
回复 23# sherf
唉,我把你那个例子描述一遍吧。
指令里出现的0x8048368就是逻辑地址的offset部分。此刻这个offset所位于的段的描述符(里面有base,limit,权限等信息)在GDT里,而某个段寄存器(CS或DS或其它)的高位用作索引在GDT里取出这个段的描述符,继而就可以得到它的base,base与offset相加,便得到了线性地址,线性地址再经分页单元根据当前页表的内容翻译成物理地址。但是Linux下每个进程在用户态下用的都是同一对段描述符(代码段和数据段),或者所有进程的用户态的cs与ds都是同一个值(继而指向GDT里的同两项);内核态的情况也是如此。这个段描述符说,此段base为0,limit为4G-1。继而base+offset = offset,也就是说,逻辑地址转换为线性地址后没有任何变化!分段和分页在功能上有重复的地方,一般用分页就够了。Linux之所以这样做是因为CPU非得走分段这个流程。这样做的结果就是,分段在地址转换过程中没有起到任何作用,只是走走过场而已。真正让进程有独立地址空间(同一个地址在不同进程里指向不同物理单元,互不影响)是由分页机制完成的。所以不要再纠结段的概念了,更不用说LDT了。
0x8048368(逻辑地址的offset)被翻译成物理地址的过程为:根据CS或DS值的高位,在GDT里找到段描述符,取其base(为0),将其与0x8048368相加(结果还为0x8048368,线性地址),然后送到分页单元。分页单元根据当前页表的内容,将其翻译成物理地址,然后送到总线上。 |
|