年初在维护一个http server程序的时候,发现5u下性能比4u下降了一倍不止。最后通过程序埋点的方法确认,问题出在calloc调用上。程序上有一段逻辑,每来一个链接,通过calloc申请一块2M的空间,在5u下calloc性能下降厉害。当时通过malloc+字段实例化的方式替换了calloc,解决了这个问题,没有太往下纠结。
今天收到封邮件,也是程序从4u升级到5u下,性能下降严重,最后定位到也是calloc的问题;但他们更进一步,分析了为啥calloc性能会下降,很不错,这里分享下。
大致的意思是:calloc性能下降是由于glibc版本不同引起的,在5u下内存分配的策略和4u不同。内存分配有两种方式:brk调用,或mmap调用;对于小空间一般在brk中分配,大空间通过mmap分配。在4u中,大小空间的阀值是定死的128K,在5u下这个阀值是动态调整的,最大可以到32M。由于分配的都是大空间,由于这个策略调整,在4u下calloc空间是通过mmap获得的,5u下是通过brk获得的。mmap分配的空间有一个特点:不发生读写操作是不会分配实际物理内存的;加载内存时,系统会把page全部清零。所以在4u下,calloc分配大内存的效率跟malloc效率差不多;而在5u下,由于在brk中分配,必须要做一次清零操作;这就是问题了。
从应用上,建议不要使用calloc函数,而改用malloc+实例化。
先简要总结一下速度降低的原因:
1. 4u和5u的