内核内存在Windows操作系统中包含什么?

时间:2010-08-31 15:19:01

标签: windows kernel virtual-memory

众所周知,在32位Windows操作系统下运行的程序只有2GB的可用虚拟内存。另外,已知其他2GB被保留为内核空间。但是那个内核空间究竟是什么呢?

我能理解内核本身所需的保留,但为什么进程的VAS中的内核空间呢?感谢。

5 个答案:

答案 0 :(得分:9)

获取Windows Internals书,它详细描述了这一点。但是,对于简短的摘要,内核虚拟地址(KVA)空间中的一些内容:

1)内核和HAL

2)设备驱动程序

3)内核模式堆(称为执行池,我总是觉得有趣)

4)通过句柄(进程,线程,事件,互斥对象等)导出到用户模式的对象

5)系统PTE,它可以映射远离grubby用户模式应用程序的各种有趣的东西(例如线程在内核模式下运行时使用的执行堆栈)

6)文件系统缓存

这个列表一直在继续......就像我说的那样,阅读Windows Internals。

-Scott

答案 1 :(得分:3)

内核内存映射到每个进程的虚拟地址空间的原因是上下文切换到内核模式不必更改进程页表。当前的权限级别仅提升到0,这会立即使这些页面可访问。

只有在切换到其他进程时才需要切换页表。由于这是一项昂贵的操作(例如,它需要TLB冲洗),因此最小化它的频率是一种胜利。

此外,如果您在特殊内核页表中执行切换,则切换到内核空间,您必须选择要替换的部分用户空间地址空间。这将使内核无法访问这些用户空间地址,这将需要反弹缓冲区或更多地址空间,以确定何时将这些区域中的数据传输到内核或从内核传输。

答案 2 :(得分:2)

在我看来,关于2GB边界还有另一个鲜为人知的事实。许多应用程序通常使用大量指针算法(尤其是用C,C ++编写的应用程序......)。在这些应用程序中,向指针添加偏移量甚至减去指针都是很常见的。

如果您的可用虚拟地址空间为2GB,则可以保证减去两个指针始终在-2147483647和+2147483648之间(这些是32位有符号值的限制)。

如果您的地址空间为3GB,则可能的差异将大于可以在32位有符号值中表示的任何值。

如果您知道您的应用程序是安全的,并且没有减去完全无关的指针(并且您的阵列小于2GB!),您可以告诉Windows您的应用程序可以使用大于2GB的地址空间,通过设置链接器标记LARGEADDRESSAWARE(或使用EDITBIN实用程序设置它)。

使用XP(对Vista和W7不太确定),您可以启动“内核空间”仅为1GB的模式,并为应用程序留出3GB的虚拟地址空间。如果您的应用程序是LARGEADDRESSAWARE,则可获得完整的3GB。如果没有,你只能获得2GB。

在64位Windows上,LARGEADDRESSAWARE 32位应用程序甚至可以获得4GB,因为Windows在32位区域内不需要大量的地址空间(毕竟,它是64位操作系统)。

答案 3 :(得分:1)

用C ++等高级语言编写的程序最终转换为OS API调用,特别是Windows OS for Windows OS。许多Windows API(如CreateFile)实际上都与内核模式驱动程序通信。进程地址空间中的内核空间用于为此进程分配内核资源。例如,驱动程序IOCTL调用包含在用户模式API和驱动程序之间传递的输入输出缓冲区。这些缓冲区在进程内核空间中分配。

通常,内核空间包含代表此进程由内核模式组件分配的资源。

答案 4 :(得分:1)

你的问题似乎是“为什么”而不是标题中提出的“什么”。

此外,您的问题假定为32位。 64位版本的Windows是完全不同的(例如,VAS是8TB,或者在Itanium系统上是7TB)。

至于“为什么”,你如何传递一个未包含在进程VAS中的内核函数(如驱动程序)的指针?阅读这本书的好书将是Windows Internals.