前言:

      有段时间没写博客了,这次写一篇水文,关于 golang log为什么加锁 ?  很水么? 对的…  

      有天同事跟我说,原来go log在写入的时候也有锁,我寻思不应该呀,为啥加锁呀。在我想来写个日志没必要加锁, 但事实来说不是这样的。 好多一些语言的日志模块也有加锁,比如 python logging 。 他加锁的目的在于 避免logrotate日志切割的时候,多线程发生冲突。  我们需要说明的是,单纯的写日志不需要加锁的,因为写日志采用了文件的O_APPEND模式,原子方式一直追加后面。 

该文章后续仍在不断的更新修改中, 请移步到原文地址  http://xiaorui.cc/?p=5195


原因

      那么golang 标准库里的log为啥加锁?  看下面的代码,我们在调用log.Print的时候,其实在调用Output。  output方法里有各种行为加锁,总结一句话,他写日志的对象是共享的,而不是每条日志分别一个Logger.buf 对象,既然不是分离的,那么要保护好buf了,要不然写串了。 

Logger 结构体对象

日志加锁操作,听起来没啥问题,但如果你的日志很疯狂输出,那么问题就来了,这么多的syscall对于性能来说很是有杀伤力。  当然,正常线上系统肯定也没人去疯狂的benchmark日志,我这边只是为了测试说明问题,syscall 是有 代价的。

下面是阿里云四核主机的cpu占用比

pprof的火焰图分析也是runtime.futex高,剩下的就是syscall Write了。


总结

    没啥总结的。 只是好奇go log为啥频繁加锁而已,算是给我解除疑惑了吧。

END.



对Python及运维开发感兴趣的朋友可以加QQ群 : 478476595 !!!
{ 2000人qq大群内有各厂大牛,常组织线上分享及沙龙,对高性能及分布式场景感兴趣同学欢迎加入该QQ群 }

另外如果大家觉得文章对你有些作用!   帮忙点击广告. 一来能刺激我写博客的欲望,二来好维护云主机的费用.
如果想赏钱,可以用微信扫描下面的二维码. 另外再次标注博客原地址  xiaorui.cc  ……   感谢!
暂无相关产品

评论已关闭。