【问题标题】:virtual to physical address conversion in linux kernelLinux内核中的虚拟地址到物理地址的转换
【发布时间】:2013-06-04 04:08:31
【问题描述】:

以下用于在linux内核中将虚拟地址转换为物理地址。但这是什么意思?

我的组装知识非常有限

163 #define __pv_stub(from,to,instr,type)                   \
164         __asm__("@ __pv_stub\n"                         \
165         "1:     " instr "       %0, %1, %2\n"           \
166         "       .pushsection .pv_table,\"a\"\n"         \
167         "       .long   1b\n"                           \
168         "       .popsection\n"                          \
169         : "=r" (to)                                     \
170         : "r" (from), "I" (type))

【问题讨论】:

    标签: linux memory-management kernel


    【解决方案1】:

    这不是真正的“汇编”,因为这个宏本身没有指令。

    它只是一个插入instr(传递给宏的指令)的宏,它有一个输入操作数from、一个立即(常量)输入操作数type和一个输出操作数to

    还有pushsectionpopsection之间的部分,它在特定的二进制部分pv_table中记录了这条指令的地址。如果内核愿意,这允许内核在其代码中找到这些位置。

    最后一部分是 asm 约束和操作数。它列出了编译器将替换 %0%1%2 的内容。 %0 是第一个列出的 ("=r"(to)),这意味着 %0 将是任何通用寄存器,即存储在宏参数 to 中的输出操作数。其他 2 个类似,除了它们是输入操作数:from 是一个寄存器,所以得到 "r",但 type 是立即数,所以 "i"

    详情请见http://gcc.gnu.org/onlinedocs/gcc-4.8.1/gcc/Extended-Asm.html#Extended-Asm

    所以考虑一下内核中的这段代码 (http://lxr.linux.no/linux+v3.9.4/arch/arm/include/asm/memory.h#L172)

    static inline unsigned long __virt_to_phys(unsigned long x)
    {       unsigned long t;
            __pv_stub(x, t, "add", __PV_BITS_31_24);
            return t;
    }
    

    __pv_stub 将等同于 t = x + __PV_BITS_31_24 (instr == add, from == x, to == t, type == @9876545)

    所以你可能想知道为什么有人会做这么复杂的事情而不是在代码中写t = x + __PV_BITS_31_24

    原因是我上面提到的pv_table。所有这些语句的地址都记录在特定的 elf 部分中。在某些情况下,内核会在运行时修补这些指令(因此需要能够轻松找到所有指令),因此需要一个表。

    ARM 端口正是在这里完成的:http://lxr.linux.no/linux+v3.9.4/arch/arm/kernel/head.S#L541

    仅在使用 CONFIG_ARM_PATCH_PHYS_VIRT 编译内核时使用:

    CONFIG_ARM_PATCH_PHYS_VIRT:
    
    Patch phys-to-virt and virt-to-phys translation functions at
    boot and module load time according to the position of the
    kernel in system memory.
    
    This can only be used with non-XIP MMU kernels where the base
    of physical memory is at a 16MB boundary, or theoretically 64K
    for the MSM machine class.
    

    【讨论】:

      猜你喜欢
      • 2019-12-06
      • 2017-07-07
      • 2018-08-12
      • 1970-01-01
      • 2017-03-10
      • 2019-07-29
      • 2011-06-17
      • 1970-01-01
      相关资源
      最近更新 更多