Intel - 80386

当我们说一个CPU是16位或32位时,指的是处理器中算术逻辑单元ALU的宽度;
系统总线中的数据线部分,称为数据总线通常与ALU宽度相同(有例外);
地址总线的宽度,最自然的是和数据总线一致;
从程序设计角度,一个地址-指针,最好与一个整数的长度一致;
出于现实考虑,地址空间太小,导致CPU内部结构的不均匀性。(8位CPU,16位地址)

Intel的16位CPU-8086采用1M的内存地址空间,地址总线的宽度20位;
虽然地址总线的宽度是20位,但CPU中ALU的宽度却只有16位...
Intel设计了一种不失巧妙的方法:
段寄存器基地址<<4 + 内部偏移地址 = 20位总线地址(实地址模式)
但是,通过改变段寄存器的内容,一个进程可以访问内存中的任何一个单元;
不能对一个进程的内存访问加以限制,谈不上对其他进程以及系统本身的保护;
一个CPU如果缺乏对内存访问的限制及保护,就谈不上什么内存管理,也就谈不上什么现代意义的CPU;

Intel-80286开始实现"保护模式",能从实地址模式转入保护模式,逆向却不行;
Intel-32位的80386实现了到现代32位CPU的飞跃;
Intel设计人员的基本思路是:
在保护模式下改变段寄存器的功能,使其从一个单纯的基地址变成一个数据结构(地址段描述结构)的指针,
* 根据指令的性质来确定应该使用哪一个段寄存器,这一点与实地址模式相同
* 根据段寄存器的内容,找到相应的"地址段描述结构"
* 从地址段描述结构中得到基地址
* 将指令中发出的地址作为位移,与段描述结构中规定的段长度相比,看看是否越界
* 根据指令的性质和段描述符中的访问权限来确定是否越权
* 将指令中发出的地址作为位移,与基地址相加得出实际的"物理地址"
从保护的角度看:
在由(指令给出的)内部地址(及逻辑地址)转换成物理地址的过程中,必须要在某个环节上对访问权限进行对比;

80386的段式内存管理机制实现:
* 新增加了2个寄存器,访问它们的专用指令设计成"特权指令":
  全局性的段描述表寄存器GDTR(global descriptor table register)
  局部性的段描述表寄存器LDTR(local descriptor table register)
  分别可以用来指向存储在内存中的一个段描述结构数组(段描述表)
* 无法通过修改描述表项的内容修改内存,起到保护作用
* 每个段描述表项的大小8字节
  [   B31 - B24   ] [G][D][A][][L19-L16]
  [P][DPL][S][type] [    B23 - B16     ]
  [            B15 - B0                ]
  [            L15 - L0                ]
 
  B31~B24 : 基地址的 bit16~bit23
  B23~B16 : 基地址的 bit24~bit31
  L19~L16 : 段长度limit的 bit0~bit15
  L15~L0  : 段长度limit的 bit16~bit19
  DPL     : 2位位段 本段特权
  P       : 0描述项无定义 1段包含有效基地址和界限
  S       : 0系统描述相 1代码或数据段描述项
  type    : 4位位段[E][ED/C][RW][A]
     E = 0 数据段
     ED 0向上伸展(数据段) 1向下伸展(堆栈段)
            W  0不可写入 1可写入
            E = 1 代码段
            C 0忽视特权级 1遵循特权级
            R 0不可读 1可读
段描述结构:
typedef struct {
  unsigned int base_24_31:8; //基地址最高8位
  unsigned int g:1; //granularity 表段长度单位 [0]字节 [1]4KB
  unsigned int d_b:1; //default operation size 存取方式 [0]16位 [1]32位
  unsigned int unused:1; //固定设置成0
  unsigned int avl:1 //avaliable,可供系统软件使用
  unsigned int seg_limit_16_19:4; //段长度的最高4位
  unsigned int p:1; //segment present, [0]该段的内容不在内存中
  unsigned int dp1:2; //Descriptor privilege level, 访问本段所需权限
  unsigned int s:1; //描述项类型 [1]系统 [0]代码/数据
  unsigned int type:4 //段的类型,与S标志位一起使用
  unsigned int base_0_23:24; //基地址的低24位
  unsigned int seg_limit_0_15:16; //段长度的低16位
}descriptor;
?? 如此奇怪 ?? 基地址的高8位和低24位为什么要拆开来 ??
Intel起先打算使用24位地址空间,后来又修修补补~~~~ 2^24 = 2^16 * 4K

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值