最近在做系统调优,总结了下cache相关知识,以及如何提高性能和并发性能的方法。
一CACHE相关
1. cache概述
cache,中译名高速缓冲存储器,其作用是为了更好的利用局部性原理,减少CPU访问主存的次数。简单地说,CPU正在访问的指令和数据,其可能会被以后多次访问到,或者是该指令和数据附近的内存区域,也可能会被多次访问。因此,第一次访问这一块区域时,将其复制到cache中,以后访问该区域的指令或者数据时,就不用再从主存中取出。
2. cache结构
假设内存容量为M,内存地址为m位:那么寻址范围为000…00~FFF…F(m位)
倘若把内存地址分为以下三个区间:
 《深入理解计算机系统》p305 英文版 beta draft  
 
tag, set index, block offset三个区间有什么用呢?再来看看Cache的逻辑结构吧:
 
将此图与上图做对比,可以得出各参数如下:
B = 2^b
S = 2^s
现在来解释一下各个参数的意义:
一个cache被分为S个组,每个组有E个cacheline,而一个cacheline中,有B个存储单元,现代处理器中,这个存储单元一般是以字节(通常8个位)为单位的,也是最小的寻址单元。因此,在一个内存地址中,中间的s位决定了该单元被映射到哪一组,而最低的b位决定了该单元在cacheline中的偏移量。valid通常是一位,代表该cacheline是否是有效的(当该cacheline不存在内存映射时,当然是无效的)。tag就是内存地址的高t位,因为可能会有多个内存地址映射到同一个cacheline中,所以该位是用来校验该cacheline是否是CPU要访问的内存单元。
当tag和valid校验成功是,我们称为cache命中,这时只要将cache中的单元取出,放入CPU寄存器中即可。
当tag或valid校验失败的时候,就说明要访问的内存单元(也可能是连续的一些单元,如int占4个字节,double占8个字节)并不在cache中,这时就需要去内存中取了,这就是cache不命中的情况(cache miss)。当不命中的情况发生时,系统就会从内存中取得该单元,将其装入cache中,与此同时也放入CPU寄存器中,等待下一步处理。注意,以下这一点对理解linux cache机制非常重要:
当从内存中取单元到cache中时,会一次取一个cacheline大小的内存区域到cache中,然后存进相应的cacheline中。
例如:我们要取地址 (t, s, b) 内存单元,发生了cache miss,那么系统会取 (t, s, 00…000) 到 (t, s, FF…FFF)的内存单元,将其放入相应的cacheline中。

二 优化性能和提高并发性的主要方法我觉得有:
1.用设计上压缩结构体大小,使整个结构体能处于一个cache line中。
2.结构体中频繁访问的字段尽量放在一个结构体的同一个cache line里面,这样可以提高cache命中率。
3为了避免cache伪共享问题,cache伪共享多发生在多核cpu的情况,比如有4个cpu,出于并发的考虑,我们可能会设立一个全局数组struct cpu_info test[4];每个cpu去访问一个test数组元素,这样会产生cache共享问题,虽然各个cpu都修改各自的数据,但他们对数据的修改,会影响到彼此各个cpu的cache访问,这就是种伪共享,解决的方法是把数据结构struct cpu_info定义成cache line对齐,即加上____cacheline_aligned前缀。
4.频繁读写的多个结构体变量尽量同时申请,使得它们尽可能的分布在较小的线性空间范围内,这样可利用TLB缓冲,提高tlb的命中率。
5.当结构体比较大时,对结构体字段进行初始化或设置值时最好从第一个字段依次往后进行,这样可保证对内存的访问是顺序进行。这样可以充分的利用cpu的cache.
6.额外的优化可以采用非暂时移动指令(如movntdq)与预读指令(如prefetchnta)。比如网卡取数据包时,在取到一个数据包进行处理时,可以使用prefech指令去取接下来的一个数据包,从而达到提高并发能力的效果。不过使用prefech指令时,最好有足够的时间让其能并发的取到,否则得不偿失,反而降低了设备性能。
7.特殊情况可考虑利用多媒体指令SSE2、SSE4等。
8memset与memecpy对于是非常耗费cpu资源的,在有可能的情况下,尽量避免对大数据结构进行memset操作,可以只对某几个字段进行赋值处理。若在必须要做memset()的情况下,可以自己开发个优化的版本,比如对于64位的机器,原始的memset()函数(来自内核2.6.18):
static inline void * __memset_generic(void * s, char c,size_t count)
{
int d0, d1;
__asm__ __volatile__(
"rep\n\t"
"stosb"
: "=&c" (d0), "=&D" (d1)
:"a" (c),"1" (s),"0" (count)
:"memory");
return s;
}
该memset()函数其实就是个循环写,每次写一个字节,慢的很。我们可以为64位开发个新的版本:
static inline void layout_memset_64(void *address, int len)
{
__u64 *addr =  (__u64 *)address;
int div = len >> 6;/*   len / 64   */
int md = len % 64;
int n = div - 1;
int ni = n<<3;/*   n*8   */
int i;

for (i = 0; i <= ni; i += 8){
*addr++  = 0;
*addr++  = 0;
*addr++  = 0;
*addr++  = 0;
*addr++  = 0;
*addr++  = 0;
*addr++  = 0;
*addr++  = 0;
}
div = md >> 3;
md %= 8;
for (i = 0; i < div; i++)
*addr++ = 0;

for (i = 0; i < md; i++){
*((__u8*)addr+i) = 0;
}
return;
}
对于64位的平台来说,每次写可以写入8个字节的数据,循环比上面的函数快了很多,会很大程度提高系统性能。
9使用大页内存,尽量提高tlb命中率,即cpu中进行地址转换的快表。大页内存一个物理页大小为4m bytes,远大于普通的4k的物理页面大小。
10对于提高多核系统的并发性,主要的调优手段主要有尽可能缩小互斥区,缩小锁的粒度,最好能避免并发的情况,比如采用类似linux 内核中per cpu的方式,同时采用并发性比较好的锁,如读写锁,互斥锁。对于一些网络设备,可以把数据会话固定分担到各个cpu,从而避免并发。

转载于:https://www.cnblogs.com/dyllove98/p/3212393.html

提高代码性能及并发性的方法浅谈相关推荐

  1. 黑盒测试用例选取方法浅谈(一)

    最近学校刚开了软件构造,要求经营自己的博客.思来想去还是决定从课堂出发,简单介绍一下黑盒测试用例的选取方法,由于精力有限,分为上下两期,每周二晚十点更新. 黑盒测试简介 黑盒测试适用于检查代码的功能的 ...

  2. SVN冲突出现原因及解决方法浅谈

    SVN冲突出现原因及解决方法浅谈 参考文章: (1)SVN冲突出现原因及解决方法浅谈 (2)https://www.cnblogs.com/andy1202go/p/8085062.html 备忘一下 ...

  3. 提高代码阅读能力的7种方法

    原文:7 Ways to Improve Your Code Reading Skills  作者: A. N. M. Bazlur Rahman  翻译:无阻我飞扬 摘要:随着越来越多的公司使用敏捷 ...

  4. 提高代码阅读能力的 7 种方法

    https://dzone.com/articles/7-ways-to-improve-your-code-reading-skill 阅读源代码是软件开发人员的工作描述.然而,这种体验并不总是愉快 ...

  5. 虚拟机 高性能服务器,3种提高虚拟机性能并最大化效率的方法

    虚拟化基础架构的真正好处是获得性能比率,而这只有通过优化VM使其有效运行而不会损害其他托管资源才能实现. 虚拟化对IT的影响是深远的,并且将继续逐年增长.基于云的服务的大量增长在一定程度上推动了许多行 ...

  6. 运用计算机优化教学的方法,浅谈计算机基础课程教学模式的优化对策论文

    计算机的应用在中国越来越普遍,改革开放以后,中国计算机用户的数量不断攀升,应用水平不断提高,特别是互联网.通信.多媒体等领域的应用取得了不错的成绩.1996年至2009 年,计算机用户数量从原来的63 ...

  7. 计算机维护与维修方法,浅谈计算机维护与维修方法

    题目:浅谈计算机维护与维修方法 作者:周旺红手机:159******** 单位:江苏省徐州机电工程高等职业学校 地址:江苏省徐州市云龙区东店子徐州机电工程高等职业学校云龙校区 邮编:221000 [摘 ...

  8. 运用计算机优化教学的方法,浅谈计算机教学中多种教学方法优化运用.doc

    浅谈计算机教学中多种教学方法优化运用 浅谈计算机教学中多种教学方法优化运用 摘 要:每一种教学方法各有其优越性,也各有其局限性,正如一把钥匙不能打开所有的锁一样,所以对于不同特点的学生群体,不同特点的 ...

  9. 如何提高模型性能?这几个方法值得尝试 | CSDN 博文精选

    2020-07-25 14:36:03 作者 | BoCong-Deng 责编 | 屠敏 出品 | CSDN 博客 封图 | CSDN 付费下载自东方 IC 写在前面 在我们进行模型训练时,如果你只是 ...

最新文章

  1. java 读写文件[多种方法]
  2. 试除法的妙用【O(√N) 复杂度】
  3. NSS_06 extjs弹出窗口上的文本框默认获得焦点
  4. 浅谈嵌套命名实体识别(Nested NER)
  5. 大数据新手的0基础学习路线,从菜鸟到高手的成长之路
  6. 2.4.5 MySQL InnoDB重做与回滚介绍
  7. Lambda表达式练习3【应用】
  8. 给一个元素插入一段HTML
  9. mysql高级之子查询,多表查询,外连接,集合操作,内部函数与数据控制_月隐学python第24课
  10. 红黄蓝收购新加坡某民营儿童教育集团,宣布更名为GEH Education...
  11. C#中主窗体Panel中加载其他多个窗体Panel控件
  12. python数据结构_(列表)大O性能_学习笔记(2)
  13. python web后端和vue哪个难_全栈开发用纯后端模板与Vue+后端框架组合哪个好?
  14. 蔚来Q4经调整净亏损17亿元 部分车型将调价
  15. 【基础教程】基于matlab疫情防护动图制作【含Matlab源码 028期】
  16. 循迹小车三个感应c语言程序,循迹小车的C语言程序(带注释)
  17. 如何安全的使用密码登录账号(在不知道密码的情况下)
  18. python cms应用生成_Django:之ORM、CMS和二维码生成
  19. w ndows10更新后变成32位了,三种直接从 Win7 升级到 Win10 的方法
  20. keyshot怎么贴logo_KeyShot实例渲染技巧教程,教你如何给产品添加有织纹的Logo

热门文章

  1. [原创].使用Nios II 9.1中的Flash Programmer无法固化程序到EPCS上
  2. 关于PyCharm无法启动的问题
  3. 精确记算程序的运行时间或者某段代码的运行时间
  4. Linux 关于动态链接库以及静态链接库的一些概念
  5. 跳转控制语句 break || continue || goto
  6. js如何判断一个对象是不是Array?
  7. Python 技术篇 - python3使用speech库常见问题原因及解决方法
  8. C语言实现牛顿迭代法
  9. jquery/css实现步骤条
  10. [YTU]_2478( C++习题 虚函数-计算图形面积)