Linux内存管理

前端之家收集整理的这篇文章主要介绍了Linux内存管理前端之家小编觉得挺不错的,现在分享给大家,也给大家做个参考。
我在读 Linux内存管理.我知道

The Linux kernel is responsible for creating and maintaining page tables but employs the cpu’s memory management unit (MMU) to translate the virtual memory accesses of a process into corresponding physical memory accesses.

但是,我也知道内核可以使用一些其功能来管理内存,如virt_to_phys(),virt_to_page(),__pa(),…

例:

static inline unsigned long virt_to_phys(volatile void *address)
{
    return __pa(address);
}

用于将虚拟地址翻译成物理地址.

我很困惑他们请帮我告诉我MMU的翻译和内核的翻译之间的关系,并区分它们?
谢谢.

解决方法

在具有虚拟内存的系统中,OS内核负责建立物理和虚拟地址之间的映射.

然而,当cpu执行访问存储器的指令时,cpu执行从进程的虚拟地址到指示存储器中实际位置的物理地址的转换.

您提到的功能可以在内核代码中使用,以获得内核代码中使用的一些地址的虚拟到物理地址的翻译.例如对于x86目标,您可以在io.h中看到virt_to_phys上的定义:

/**
 *  virt_to_phys    -   map virtual addresses to physical
 *  @address: address to remap
 *
 *  The returned physical address is the physical (cpu) mapping for
 *  the memory address given. It is only valid to use this function on
 *  addresses directly mapped or allocated via kmalloc.
 *
 *  This function does not give bus mappings for DMA transfers. In
 *  almost all conceivable cases a device driver should not be using
 *  this function
 */

static inline phys_addr_t virt_to_phys(volatile void *address)
{
    return __pa(address);
}

如果你遵循__pa(地址)的定义,你会看到它最后调用__phys_addr,它被定义为:

unsigned long __phys_addr(unsigned long x)
{
    if (x >= __START_KERNEL_map) {
        x -= __START_KERNEL_map;
        VIRTUAL_BUG_ON(x >= KERNEL_IMAGE_SIZE);
        x += phys_base;
    } else {
        VIRTUAL_BUG_ON(x < PAGE_OFFSET);
        x -= PAGE_OFFSET;
        VIRTUAL_BUG_ON(!phys_addr_valid(x));
    }
    return x;
}

因此,您可以看到内核正在使用偏移量从虚拟地址中计算物理地址.根据代码为翻译编译的体系结构将不同.而对于virt_to_phys的评论,这只适用于通过kmalloc直接映射或分配的内核中的内存,它不会将任意物理映射到虚拟地址.该翻译依赖于查找页表映射.

在任一情况下,作为内核一部分在cpu上执行的实际指令仍然依赖于cpu的MMU从其操作的虚拟地址转换为数据实际位于内存中的物理地址.

原文链接:https://www.f2er.com/linux/393853.html

猜你在找的Linux相关文章