按位移位以查找内存地址的一部分

问题描述

这是一个测试程序,试图让我的按位移位操作工作。我希望将此添加到我的缓存模拟器程序中,但我什至无法让这部分工作。我的计划是使用位移 (>) 来隔离给定内存地址的部分(标记、集合、字等),但似乎在将位向右移回时,它填充了以前存在的值,而不是 0。首先是程序。

#include<iostream>
#include <cmath>

struct Address{
    unsigned int tag;
    unsigned int r;
    unsigned int word;
};

int main(){
    unsigned int tempAddress = 27; //0011011
    int ramSize = 128;
    int cacheSize = 64;
    int blockSize = 8;

    int cacheLines = cacheSize / blockSize;

    int addressLength = log(ramSize)/log(2);
    int wordBits = log(blockSize)/log(2);
    int rBits = log(cacheLines)/log(2);
    int tagBits = addressLength - (wordBits + rBits);

    struct Address address;

    address.tag = tempAddress >> (rBits + wordBits);
    address.r = tempAddress << (tagBits) >> (tagBits + wordBits);
    address.word = tempAddress << (rBits + tagBits) >> (rBits + tagBits);

    std::cout << "tag is: " << address.tag << "\n";
    std::cout << "r is: " << address.r << "\n";
    std::cout << "word is: " << address.word << "\n";


}

我发现当我的 tempAddress 是 [0-7] 时它工作正常,因为二进制 7 只影响前 3 位。 同样,当是[8-63]时,tag和r都是正确的,因为63影响了前6位。 在测试了许多地址后,我发现在左移后右移时,这些位被替换为之前的位,而不是我认为应该是的 0。

(r 是中间的部分。我叫它 r 因为在直接映射中它被称为 line,而在集合关联映射中它被称为 set)

编辑:

正如有人指出的那样,预期和产生的结果会有所帮助。我想先保持缓存大小、内存大小和块大小不变,只更改地址。

因此,给定 tempAddress = 27(二进制的 0011011),word 应该是 011(前 3 位),r 应该是 011(接下来的 3 位),set 应该是 0(剩余位)。 输出是这样的:

tag is: 0
r is: 3
word is: 27

如果标记和 r 之间的 0 到 63(含)之间的每个地址都是正确的,但字等于地址,我发现这是趋势。

现在,对于地址 = 65(1000001) 预期:

tag is: 1
r is: 0
word is: 1

输出

tag is: 1
r is: 8
word is: 65

有了这些内存、缓存和块大小,为了找到 r,我左移 1 次,右移 4 次。为了找到单词,我左移 4 次,然后右移 4 次。据我了解,当左移右边的位时用 0 填充,当右移一个无符号整数时,左边的位用 0 填充。我的想法是,如果我左移直到我只有这些位我需要,然后将它们右移回第一位,我将获得正确的值。但是,在众多地址中一致,左移后右移后,有1的地方仍然如此。这就是为什么字总是等于地址的原因,因为我正在向左然后向右移动 4 位。并且 r 总是等于 7 位右移 3 次(因为我向左移动 1 然后向右移动 4)。我是否误解了按位移位的工作原理?

解决方法

暂无找到可以解决该程序问题的有效方法,小编努力寻找整理中!

如果你已经找到好的解决方法,欢迎将解决方案带上本链接一起发送给小编。

小编邮箱:dio#foxmail.com (将#修改为@)