Memory 为什么x86#u64内核中有这么大的虚拟地址';内存布局

Memory 为什么x86#u64内核中有这么大的虚拟地址';内存布局,memory,linux-kernel,x86-64,virtual-address-space,address-space,Memory,Linux Kernel,X86 64,Virtual Address Space,Address Space,内核的文档/x86/x86_64/mm.txt说: ffff880000000000 - ffffc7ffffffffff (=64 TB) direct mapping of all phys. memory 所以我假设在这个区域中不应该有大于实际物理DRAM大小的地址映射。但在带有16GB DRAM和内核v4.2.8的x86_64 PC上,我从/sys/kernel/debug/kernel_page_表中得到了以下结果: ---[ Low Kernel Mapping ]--- ...

内核的文档/x86/x86_64/mm.txt说:

ffff880000000000 - ffffc7ffffffffff (=64 TB) direct mapping of all phys. memory
所以我假设在这个区域中不应该有大于实际物理DRAM大小的地址映射。但在带有16GB DRAM和内核v4.2.8的x86_64 PC上,我从/sys/kernel/debug/kernel_page_表中得到了以下结果:

---[ Low Kernel Mapping ]---

......

0xffff88008b3ff000-0xffff88008b400000           4K     RW                 GLB NX pte

0xffff88008b400000-0xffff8800c0000000         844M                               pmd

0xffff8800c0000000-0xffff880100000000           1G                               pud

0xffff880100000000-0xffff880400000000          12G     RW         PSE     GLB NX pud

0xffff880400000000-0xffff88043dc00000         988M     RW         PSE     GLB NX pmd

0xffff88043dc00000-0xffff88043dc25000         148K     RW                 GLB NX pte

0xffff88043dc25000-0xffff88043dc27000           8K     ro                 GLB NX pte

.......

0xffff88045c200000-0xffff88046f000000         302M     RW         PSE     GLB NX pmd

0xffff88046f000000-0xffff880480000000         272M                               pmd

0xffff880480000000-0xffff888000000000         494G                               pud

0xffff888000000000-0xffffc90000000000       66048G                               pgd
您可以看到,有虚拟地址为0xffff88043dc00000的页面条目,使用 该虚拟地址上的virt_to_phys()将获得0x43dc00000,即 显然是非法的,因为它比实际的DRAM大小大(16GB只是 0x400000000)

那么,这些大型虚拟地址的规则是什么?如何才能为其获得正确的物理地址


非常感谢

您的电脑不仅有DRAM,还有ROM(现在是闪存)和I/O内存。为了向后兼容,其中的一部分必须映射到20位和32位地址空间,因此RAM的最后一部分最终位于0x400000000以上的某个地址。

物理地址不仅仅用于RAM。连接到机器的不同设备也有一些物理地址。处理器只是将物理地址放在地址总线上,一个或多个设备将响应它

因此,在您的情况下,这些物理地址可能是一些IO设备,如ROM(CD-ROM等)


此外,RAM的物理地址也可能大于16GB。这取决于它放在哪里。

谢谢!我终于在[link]上找到了一个介绍,上面有一张展示整个内存布局的漂亮图片。我遇到的另一个问题是,这个大地址似乎无法用于DMA操作,因此我假设该地址位于“主存回收地址范围”内。我从virt_到_phys()获得的地址与DDR控制器视图中的地址不同,这一差异导致该地址无法用于DMA。如果我错了,请纠正我