为什么MySQL死锁检测会严重降低TPS

 

在大量的客户端,更新数据表的同一行时,会造成数据库的吞吐量大幅降低。

很多数据库的前辈和同行分别通过实验和源码的方法,定位到了罪魁祸首----MySQL死锁检测

实验方式:http://blog.csdn.net/zhaiwx1987/article/details/6952285

源码方式:http://www.gpfeng.com/?p=426

请大家尤其注意这段代码

#####

lock_mutex_enter();

ut_ad(lock_table_has(thr_get_trx(thr), index->table, LOCK_IX));

err = lock_rec_lock(TRUE, LOCK_X | LOCK_REC_NOT_GAP,
block, heap_no, index, thr);

MONITOR_INC(MONITOR_NUM_RECLOCK_REQ);

lock_mutex_exit();

#####

可以看出,MySQL在试图获取锁期间,会有lock_mutex_enter 和lock_mutex_exit保护。

  在一般情况下,lock_rec_lock执行速度很快,所以不成问题。

  但是如果有大量锁等待的情况,比如多个客户端试图更新同一行,则这个过程非常缓慢。因此整个innodb层就由并行变成了串行,大幅降低TPS。

  解决办法:

   让锁等待尽量少,可以通过在数据库层设置等待队列达到这个效果,而OneSQL内置了这个方案。     

 测试用例:

       update miaosha set mount=mount+1 where id=1;

  测试环境

  MySQL和OneSQL的关键参数配置如下,且均未开启binlog

数据库 innodb_flush_log_at_trx_commit innodb_log_file_size innodb_buffer_pool_size
OneSQL 1 1000M 8G
MySQL 1 1000M 8G


  硬件环境 

 

 

内存 cpu 磁盘
32g 8c 每个core上有两个超线程
Intel(R) Xeon(R) CPU
 E5620  @ 2.40GHz
2块raid0
7500r

测试结果:      

       在512个线程情况下,TPS为500/s

      

       我实际测试,同样的环境下使用OneSQL,TPS可以达到15682/s,性能提升达30倍左右。

       

 如有任何疑问,请联系微信onesoft007

posted @ 2015-08-05 22:22  友哥  阅读(1976)  评论(1编辑  收藏  举报