5.3.1 FCSE概述
FCSE(Fast Context Switch Extension,快速上下文切换)位于CPU和MMU之间,如果两个进程使用了同样的虚拟地址空间,则对CPU而言,两个进程使用了同样的虚拟地址空间。快速上下文切换机构对各进程的虚拟地址进行变换,这样系统中除了CPU之外的部分看到的是经过快速上下文切换机构变换的虚拟地址。快速上下文切换机构将各进程的虚拟空间变换成不同的虚拟空间,这样在进行进程间切换时就不需要进行虚拟地址到物理地址的重映射。
快速上下文切换(FCSE)通过修改系统中不同进程的虚拟地址,避免在进行进程间切换时造成的虚拟地址到物理地址的重映射,这样就减少了重建MMU、使cache和TLB无效、重建cache和TLB内容等操作的巨大开销,从而提高系统的性能。
在ARM系统中,4GB的虚拟空间被分成128个进程空间块,每个进程空间块大小为32MB。每个进程空间块中可以包含一个进程,该进程可以使用虚拟地址空间0x00000000~0x01ffffff,这个地址范围也就是CPU看到的进程的虚拟空间。系统128个进程空间块的编号为0~127,编号为I的进程空间块中的进程实际使用的虚拟地址空间为I*0x02000000到I*0x02000000+ 0x01ffffff,这个地址空间是系统中除了CPU之外的其他部分看到的该进程所占用的虚拟地址空间。
快速上下文切换机构将CPU发出的每个虚拟地址按照上述的规则进行变换,然后发送到系统中的其他部分,变换过程如图5-1所示。
图5-1 FCSE原理框图
图5-1中地址VA到MVA的变换算法如下:
if (VA[31:25] == 0b0000000) then
MVA = VA | (PID <<25)
else
MVA = VA
如果VA[31:25]不等于0,说明地址VA是本进程用于访问其他进程中的数据和指令的虚拟地址,此时被访问进程的PID不能为0。相反如果VA[31:25]等于0,说明要访问的地址VA在该进程自身地址空间内,所以要进行进程上下文切换,将VA转换成MVA,其中上面公式中的PID是该进程的PID号。
ARM处理器用CP15协处理器的C13寄存器来实现FCSE功能,C13寄存器的介绍详见第4.1.2节“CP15寄存器介绍”。当要进行进程切换时,首先清空写缓存,再把新进程的页表地址写入CP15的C2寄存器,然后把新进程的PID号写入CP15的C13寄存器的最高7位即可。如果处理器不支持FCSE功能,那么使cache和TLBs无效,然后系统要重建cache和TLBs。下面我们比较一下XScale处理器以及ARMv6处理器中进程切换中的内存切换操作函数的区别:
XScale处理器进程切换中的内存切换操作函数如下所示:
.align 5
ENTRY(cpu_xscale_switch_mm)
clean_d_cache r1, r2 ;使r1所指地址到r2所指地址之间数据cache无效
mcr p15, 0, ip, c7, c5, 0 ;使系统全部指令cache无效
mcr p15, 0, ip, c7, c10, 4 ;清空写缓存Write Buffer
mcr p15, 0, r0, c2, c0, 0 ;装入新的页表地址
mcr p15, 0, ip, c8, c7, 0 ;使系统全部数据和指令TLBs cache无效
cpwait_ret lr, ip ;返回
ARMv6处理器进程切换中的内存切换操作函数如下所示:
ENTRY(cpu_v6_switch_mm)
mov r2, #0
ldr r1, [r1, #MM_CONTEXT_ID] ;获取新进程的PID号,该PID号其实就是新进程的struct mm_struct结构中的mm_context_t成员结构context的id
mcr p15, 0, r2, c7, c10, 4 ;清空写缓存Write Buffer
mcr p15, 0, r0, c2, c0, 0 ;装入新的页表地址
mcr p15, 0, r1, c13, c0, 1 ;设置上下文PID号
mov pc, lr ;返回
在ARM处理器中只有ARMv6以上版本的处理器才支持FCSE功能。