CPU高速缓存行

来源:互联网 发布:c 语言入门级书籍 编辑:程序博客网 时间:2024/06/03 18:26

高速缓存行:当一个数据需要反复使用的时候,我们就会把该数据读入CPU的高速缓存行(内存读取数据太慢),可以说高速缓存行大大提高了程序性能
但是在多处理器的计算机上,高速缓存行却有一个重大的问题
在芯片设计合理的情况下
假设,两个CPU需要读取同一个字节
1.CPU0读取一个字节,并把它写入CPU0的高速缓存行
2.CPU1读取一个字节,并把它写入CPU1的高速缓存行
3.CPU0修改这个字节,CPU1被告知这个情况,CPU1的高速缓存行无效
4.CPU1重新读取内存的值,并写入高速缓存行
这里我们就发现多个CPU读取的相同的内存地址中的值,会因为其中一个CPU的修改造成另外一个CPU的缓存无效

假设,我们把只读数据与读写数据放在一起,就会造成CPU反复读取内存,写入高速缓存行,所以,以上告诉我们,高速缓存行中存储块的数据应该合理的组合,比如把读与写的数据放入不同的高速缓存行

下面举个例子:
struct
{
DWORD dwCustomerID;//read-only
int nBalanceDue;//read-write
char szName[100];//read-only;
FILETIME ftLastOrderData;//read-write;
}
//这个结构设计的非常不合理,
1当CPU读取dwCustomerID时,一定会读到nBalanceDue,为什么呢,因为高速缓存行需要字节对齐,对于X86来说是32个字节,对于其他的是64个字节,多处理器计算机中,nBalanceDue的写会造成高速缓存行的失效
2.没有注意字节的对齐
现在我们看下另一个结构

#ifdef _X86_#define CACHE_ALIGN 32#endif#ifdef _ALPHA#define CACHE_ALIGN 64#endif#define CACHE_PAD(Name,BytesSofar) (BYTE Name[CACHE_ALIGN-((BytesSofar)%(CACHE_ALIGN))])struct CUSTINFO{DWORD dwCustomerID;//read-onlychar szName[100];//read-only;//填充数据,字节对齐,接下来的数组强迫下面的成员到另一个高速缓存行CACHE_PAD(bPad1,sizeof(DWORD)+100);int nBalanceDue;//read-writeFILETIME ftLastOrderDate;//read-write//填充数据,字节对齐CACHE_PAD(bPad2,sizeof(int)+sizeof(FILETIME));}

这个结构,使用一个没有意义的数组去填充只读与读写数据之间的间隙,既使字节能够对齐,又可以让两组数据位于不同的高速缓存行