本文介绍了请问虚拟内存区域结构只进入画面时,有一个页面错误?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

虚拟内存对我来说是一个非常复杂的话题。我试图去了解它。这里是我的一个32位系统的了解。例如,RAM仅2GB。我曾尝试阅读环节多,而我此刻不自信。我想你的人来帮我清理了我的概念。请谅解我的观点,还请回答你的感觉是错的。我也有我的点糊涂部分。所以,在这里开始了总结。


  1. 每个进程都认为它只是运行。它可以访问4GB内存 - 虚拟地址空间


  2. 当一个进程访问虚拟地址,它被翻译通过MMU物理地址。
    这个MMU是CPU的一部分 - 一个硬件。


  3. 在该MMU不能将地址转换为物理的,它提出了一个页面错误。


  4. 在页面错误,内核通知。内核检查虚拟机区域结构。如果能找到它 - 可能是在磁盘上。它会做一些页面入/出页面。并获得了RAM此内存。


  5. 现在MMU将再次尝试,必将获得成功这个时候。


  6. 在情况下,内核不能找到地址,它会提高信号。例如,无效的访问都将引发一个SIGSEGV。


困惑点。


  1. 请问页表保持在内核?这VM区域结构有一个页表?


  2. 如何MMU找不到物理内存地址。比方说,将其转换为在RAM中一些错误的地址。仍然是code将执行,但是这将是一个错误的地址。 MMU如何确保它读取正确的数据?是否请教内核虚拟机区域每次?


  3. 是映射表 - 虚拟到物理是一个MMU内。我已阅读它是由一个单独的进程维护。如果它是一个过程里面,我为什么不能看到它。
    或者如果它是MMU,MMU如何产生地址 - 它是该段+ 12位的移位 - >网页帧号,然后加入偏移(位-1〜10) - >给出一个物理地址。
    这是否意味着,对于一个32位结构,这种计算在我的脑海。我可以从虚拟地址确定物理地址。


  4. 执行cat / proc / pid_value /地图。这说明我vmarea的当前映射。基本上,它读取Vmarea结构并打印。这意味着,这是很重要的。我不能够在完整的图片,以适应这一块。当执行该程序确实产生vmarea结构。是VMAREA来,只有到当MMU cannnot转换地址,即页错了吗?当我打印vmarea它显示的地址范围,权限,并映射到文件描述符,和偏移量。我相信这文件描述符是一个在硬盘和偏移量是该文件。


  5. 高-MEM概念是内核不能直接访问存储区大于1GB(约)更大。因此,它需要一个页面表来间接映射。因此,它会暂时加载一些页面表来映射地址。是否高MEM将进入图片每次。因为用户空间可以直接转化通过MMU的地址。在什么情况下,没有真正的内核要访问的高MEM。我相信内核驱动程序将主要通过kmalloc进行。这是一个直接存储器+偏移地址。在这种情况下,真正需要的任何映射。因此,问题是在一个内核需要访问高纪念品是什么情景。


  6. 请问处理器专门配备了MMU的支持。这些谁没有MMU支持不能运行Linux?



解决方案

Yes. Not exactly: each process has a mm_struct, which contains a list of vm_area_struct's (which represent abstract, processor-independent memory regions, aka mappings), and a field called pgd, which is a pointer to the processor-specific page table (which contains the current state of each page: valid, readable, writable, dirty, ...).

The page table doesn't need to be complete, the OS can generate each part of it from the VMAs.

The translation fails, e.g. because the page was marked as invalid, or a write access was attempted against a readonly page.

There are two kinds of MMUs in common use. One of them only has a TLB (Translation Lookaside Buffer), which is a cache of the page table. When the TLB doesn't have a translation for an attempted access, a TLB miss is generated, the OS does a page table walk, and puts the translation in the TLB.

The other kind of MMU does the page table walk in hardware.

In any case, the OS maintains a page table per process, this maps Virtual Page Numbers to Physical Frame Numbers. This mapping can change at any moment, when a page is paged-in, the physical frame it is mapped to depends on the availability of free memory.

To a first approximation, yes. Beyond that, there are many reasons why the kernel may decide to fiddle with a process' memory, e.g: if there is memory pressure it may decide to page out some rarely used pages from some random process. User space can also manipulate the mappings via mmap(), execve() and other system calls.

Totally unrelated to the other questions. In summary, high memory is a hack to be able to access lots of memory in a limited address space computer.

Basically, the kernel has a limited address space reserved to it (on x86, a typical user/kernel split is 3Gb/1Gb [processes can run in user space or kernel space. A process runs in kernel space when a syscall is invoked. To avoid having to switch the page table on every context-switch, on x86 typically the address space is split between user-space and kernel-space]). So the kernel can directly access up to ~1Gb of memory. To access more physical memory, there is some indirection involved, which is what high memory is all about.

Laptop/desktop processors come with an MMU. x86 supports paging since the 386.

Linux, specially the variant called µCLinux, supports processors without MMUs (!MMU). Many embedded systems (ADSL routers, ...) use processors without an MMU. There are some important restrictions, among them:

  • Some syscalls don't work at all: e.g fork().
  • Some syscalls work with restrictions and non-POSIX conforming behavior: e.g mmap()
  • The executable file format is different: e.g bFLT or ELF-FDPIC instead of ELF.
  • The stack cannot grow, and its size has to be set at link-time.

When the kernel loads a program, it will setup several VMAs (mappings), according to the segments in the executable file (which on ELF files you can see with readelf --segments), which will be text/code segment, data segment, etc... During the lifetime of the program, additional mappings may be created by the dynamic/runtime linkers, by the memory allocator (malloc(), which may also extend the data segment via brk()), or directly by the program via mmap(),shm_open(), etc..

The VMAs contain the necessary information to generate the page table, e.g. they tell whether that memory is backed by a file or by swap (anonymous memory). So, yes, the kernel will update the page table by looking at the VMAs. The kernel will page in memory in response to page faults, and will page out memory in response to memory pressure.


Using x86 no PAE as an example:

On x86 with no PAE, a linear address can be split into 3 parts: the top 10 bits point to an entry in the page directory, the middle 10 bits point to an entry in the page table pointed to by the aforementioned page directory entry. The page table entry may contain a valid physical frame number: the top 22 bits of a physical address. The bottom 12 bits of the virtual address is an offset into the page that goes untranslated into the physical address.

Each time the kernel schedules a different process, the CR3 register is written to with a pointer to the page directory for the current process. Then, each time a memory access is made, the MMU tries to look for a translation cached in the TLB, if it doesn't find one, it looks for one doing a page table walk starting from CR3. If it still doesn't find one, a GPF fault is raised, the CPU switches to Ring 0 (kernel mode), and the kernel tries to find one in the VMAs.

On x86, yes, the MMU does the page table walk. On other systems (e.g: MIPS), the MMU is little more than the TLB, and on TLB miss exceptions the kernel does the page table walk by software.

这篇关于请问虚拟内存区域结构只进入画面时,有一个页面错误?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

09-02 21:05