分页内存和非分页内存

本文介绍了WindowsNT操作系统中虚拟内存的概念,并详细解释了分页内存和非分页内存的作用及区别。非分页内存用于存放必须常驻内存的数据和代码,而分页内存则存放可以被换出到磁盘的数据。

分页内存和非分页内存  

首先介绍几个术语:

进程上下文,就是表示进程信息的一系列东西,包括各种变量、寄存器以及进程的运行的环境。这样,当进程被切换后,下次再切换回来继续执行,能够知道原来的状态。
中断上下文,就是中断发生时,原来的进程执行被打断,那么就要把原来的那些变量保存下来,以便中断完成后再恢复。

Windows NT和Windows 98都是运行在支持虚拟地址空间的计算机上,虚拟地址空间或者映射到一段真实的物理内存,或者映射到交换文件中的页帧。

每一个进程有4G的虚拟地址空间空间(因为一般机器是32位),这4G的空间被分为用户模式地址空间以及用户模式地址空间。无论何时我们需要访问计算机内存,都要使用内核模式的虚拟地址。每一个用户模式进程都有自己的地址上下文,记录了进程信息的一系列东西。当Windows NT调度器把控制从一个进程的当前线程切换到另一个进程的某个线程时,与进程相对应的虚拟地址空间也被更换(执行到别的进程了,也就是跑到另外的一个4G的地址)。线程切换的一个步骤就是改变处理器当前使用的页表,以便它能引用新线程的进程上下文。

虚拟内存系统的特征就是能使软件有一个比物理内存大得多的虚拟内存空间。为了做到这一点,内存管理器需要在物理内存和磁盘文件间交换页帧。但操作系统的某些部分是不能被分页的,这些内存用来支持内存管理器本身。最明显的例子就是,用于处理页故障的代码和数据结构必须常驻内存。

Windows NT把内核模式地址空间分成分页内存池和非分页内存池。(用户模式地址空间总是分页的) 必须驻留的代码和数据放在非分页池;不必常驻的代码和数据放在分页池中。Windows NT为决定代码和数据是否需要驻留非分页池提供了一个简单规则

非分页内容的空间是很小的,所以一般的东西都会放入分页内存中。

执行在高于或等于DISPATCH_LEVEL级上的代码必须存在于非分页内存中。

<think>我们正在讨论Windows内存管理中的分页内存非分页内存。根据引用[1][3],我们可以知道: - 分页内存(Paged Memory)是指可以被交换到磁盘上的内存页,当物理内存不足时,操作系统可以将这些页换出到磁盘,需要时再换入。 - 非分页内存(NonPaged Memory)则是必须常驻在物理内存中的内存页,不能被交换到磁盘。 引用[3]还提到了在DDK(Driver Development Kit)中如何通过代码段数据段的编译指令来指定代码或数据是分页还是非分页的。 现在,我们需要详细解释两者的区别,包括它们的定义、使用场景、访问限制等。 结合IRQL的知识(用户之前的问题),我们知道在IRQL >= DISPATCH_LEVEL(即2)时,不能访问分页内存,因为此时系统无法处理缺页中断(page fault),所以必须使用非分页内存。 因此,我们可以这样组织回答: 1. 定义分页内存非分页内存。 2. 解释为什么需要非分页内存(主要是在高IRQL下不能处理缺页中断)。 3. 说明在驱动开发中如何指定代码或数据为非分页(使用DDK提供的宏)。 4. 使用场景:分页内存用于一般情况,非分页内存用于中断处理、DPC等运行在高IRQL的代码或数据。 5. 性能影响:非分页内存会减少可用物理内存,因此应谨慎使用。 另外,引用[2]提到了分段分页,但我们的问题聚焦在分页非分页内存,所以可以略过分段的内容。 我们还需要注意,在回答中要自然地添加引用标识,如[^1][^3]等。 最后,生成相关问题。 下面开始回答:</think>### Windows内存管理中分页内存非分页内存的区别 #### 1. **核心定义** - **分页内存 (Paged Memory)** 可被交换到磁盘的虚拟内存区域。当物理内存不足时,操作系统会将这部分内存内容暂存至硬盘的页面文件(Pagefile.sys),需要时再加载回内存[^1][^3]。 **特点**: - 允许访问时触发缺页异常(Page Fault) - 仅能在 IRQL < `DISPATCH_LEVEL`(即0或1)时访问 - 通过 `PAGED_CODE()` 宏或 `#pragma alloc_text(PAGE, ...)` 指定 - **非分页内存 (NonPaged Memory)** 必须常驻物理内存的区域,不能被交换到磁盘[^1][^3]。 **特点**: - 禁止触发缺页异常 - 可在任意 IRQL(包括 `DISPATCH_LEVEL` 及以上)访问 - 通过 `NonPagedPool` 分配或 `#pragma alloc_text(INIT, ...)` 指定 #### 2. **技术原理对比** | **特性** | **分页内存** | **非分页内存** | |------------------------|----------------------------------|--------------------------------| | **交换机制** | 可交换到磁盘 | 永久驻留物理内存 | | **缺页异常处理** | 允许触发 | 禁止触发 | | **IRQL 访问限制** | 仅限 IRQL < 2 | 任意 IRQL (0~31) | | **内存分配函数** | `ExAllocatePoolWithTag(PagedPool)` | `ExAllocatePoolWithTag(NonPagedPool)` | | **典型应用场景** | 用户态程序、低IRQL驱动代码 | 中断处理、DPC、自旋锁临界区 | #### 3. **访问限制的本质** 在 IRQL ≥ `DISPATCH_LEVEL` 时(如硬件中断处理中): - **分页内存访问风险**: 若触发缺页异常,系统需执行磁盘I/O加载页面,但高IRQL下线程调度被禁用,无法等待I/O完成,导致系统崩溃(蓝屏错误 `IRQL_NOT_LESS_OR_EQUAL`)[^1]。 - **非分页内存安全性**: 物理地址始终有效,无需页面加载,避免上述问题。 #### 4. **开发实践示例 **驱动代码中的显式声明: ```c // 声明非分页内存中的函数(可在高IRQL运行) #pragma alloc_text(INIT, DriverHighIrqlRoutine) // 声明分页内存中的函数(仅低IRQL运行) #pragma alloc_text(PAGE, DriverLowIrqlRoutine) // 分配非分页内存(中断处理中使用) PVOID buffer = ExAllocatePool2(NonPagedPool, size, 'TAG'); ``` #### 5. **典型应用场景** - **分页内存适用**: - 文件系统缓存 - 用户态进程内存 - 驱动中不涉及中断的常规逻辑 - **非分页内存必需**: - 中断服务例程 (ISR) - 延迟过程调用 (DPC) - 自旋锁保护的临界区 - 设备DMA缓冲区 > **关键设计原则**:非分页内存占用应最小化,因其减少可用物理内存,过度使用会导致系统频繁换页,降低性能[^3]。 ---
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值