虚拟内存页面对齐

时间:2013-11-21 05:51:08

标签: bit-manipulation virtual-memory bitmask

遇到此算法以计算给定地址的页面偏移量。

 //naive solution:
int getAlignedValue(int pageSize, int valueToAlign)
{
    int index = valueToAlign/pageSize;
    return index * pageSize;
}

//faster solution:
int getAlignedValue_Fast(int pageSize, int valueToAlign)
{
    return valueToAlign & (~(pageSize-1));
}

天真的方法很简单直观,但更快的解决方案只有在页面大小为2的幂时才有效。例如,

pagesize = 8
address = 30
getAlignedValue(8,30) => 24
getAlignedValue_Fast(8,30) => 24

However, when the pagesize is not a power of 2, such as 10
pagesize = 10
address = 24
getAlignedValue(10,24) => 20
getAlignedValue_Fast(10,24) => 16 //wrong

我的问题是当页面大小为2的幂时,更快的方法使用什么属性,以便valueToAlign & (~(pageSize-1))“碰巧”返回正确的对齐,例如24.换句话说,从逐位比较中,我所理解的只是它在某种程度上有效,但却没有理解它背后的数学。

//leading 0s are ignored
pagesize = 8 => 00001000, address = 30 => 00011110
=>
~(pagesize - 1) = ~(00000111) = > 11111000 
=>
 00011110
&11111000
----------
 00011000 = 24

非常感谢。

1 个答案:

答案 0 :(得分:0)

如果pageSize是2的幂(即,它只设置了1位),那么~(pageSize - 1)(相当于大多数系统上的~pageSize + 1-pageSize)仍然具有该特定位,并且所有更高位也被设置:

pageSize     = 00001000  // bit k is set
// now the -1 will borrow through all rightmost zeroes and finally reset the 1
pageSize-1   = 00000111  // all bits < k are set
// inverting restores the original 1 and also sets all higher bits
~(pageSize-1)= 11111000  // all bits >= k are set

AND-ing与pageSize对齐,因为,例如,与8对齐意味着没有设置“值小于8”的位。掩模留下8(在这个例子中)和所有更高的2的幂,但是两个(1,2和4)的所有较低的力被移除。