直接在内存中写入数据和使用asm指令之间的区别

时间:2013-07-17 07:07:45

标签: memory assembly

我正在阅读Linux内核。我很想知道在内存中写入数据的方法。

在某些驱动程序中,它们使用writel()中定义的asm/io.h函数,在该函数的定义中,它们使用movnti指令 - 实际上我不明白这是什么指令意味着除了它是一种mov指令。

无论如何,在内存中写入数据时,使用writel()和直接写入内存之间有什么区别,例如 **address = data;

情况如下:

static inline void __writel(__u32 val, volatile void __iomem *addr)
{
    volatile __u32 __iomem *target = addr;
    asm volatile("movnti %1,%0"
             : "=m" (*target)
             : "r" (val) : "memory");
}

这是另一种情况:

*(unsigned int*)(MappedAddr+pageOffset) = result;

2 个答案:

答案 0 :(得分:2)

writel看起来像是用于内存映射IO,有一些东西要支持这个,首先使用volatile指针(这会阻止优化,例如重新排序调用或优化它们之间)其他事情)和非temproal指令(IO写/读不应该被缓存)当然iomem注释似乎也支持这一点。

答案 1 :(得分:1)

如果我正确理解this,那么使用moventi指令将最大限度地减少对处理器数据缓存的影响。使用*(unsigned int*)(MappedAddr+pageOffset) = result;代替编译器自由选择它喜欢的move指令,并且它可能选择一个导致缓存行被拉入缓存的指令。如果您正在与内存映射设备进行交互,那么这可能不是您想要的。