------------------------------------------------------ 2015-02-10------------------------------------------------------ mysql
本文只是简单介绍 msyql master thread 工做方式, 了解便可.sql
innodb 存储引擎的主要工做都在一个单独的后台线程中完成的.数据库
master thread 具备最高的线程优先级. 其内部又多个循环组成. : 主循环(loop),后台循环(background loop), 刷新循环(flush loop), 暂停循环(suspend loop). master thread 会跟据mysql运行状态在这几个循环中进行切换.缓存
loop :服务器
被称为主循环,由于大多数操做是在这个循环中进行的. 主循环使用 thread sleep来实现每秒/每10秒的间隔, 因此,这并不必定精确. 在负载很大的状况下,可能会有延迟.并发
每秒一次的操做包括 :函数
1.日志缓冲刷新到磁盘, 即便事务没有提交(commit).oop
注意! 即便事务没有提交操做, innodb 重作日志缓存仍然会刷新到重作日志文件, 因此就算很大的事务操做的commit没有想象中那么慢. 性能
2.合并插入缓冲(可能);测试
合并插入缓冲不必定每秒都执行, innodb引擎会判断当前1秒内发生的IO次数是否小于5次, 若是小于5次.则合并插入缓冲.
3. 最多刷新100个 innodb缓冲池中的脏页到磁盘(可能)
innodb存储引擎经过判断当前缓冲池中脏页的比例()是否超过配置文件中innodb_max_dirty_pages_pct这个参数的值(默认为90, 表示90%).若是超过了这个阀值 ,innodb存储引擎则认为须要作磁盘同步操做,刷新100个脏页到磁盘.
4. 若是当前用户没有活动, 切换到 background thread (可能)
每10秒执行的操做 :
1 .刷新100个脏页到磁盘 (老是)
2. 合并最多5个插入缓冲(老是)
3. 将日志缓冲刷新到磁盘(老是)
4. 删除无用的Undo页(老是)
5. 刷新100个或者10个脏页到磁盘(老是)
在10秒的循环操做中. innodb存储引擎首先判断过去10秒内的磁盘IO操做是否小于200次, 若是小于,则将100个脏页刷新到磁盘. 而后合并 (最多5个)插入缓冲, 而后将重作日志缓冲刷新到日志文件.而后,innodb存储引擎会执行一次full purge. 既删除无用的undo页. 对表(磁盘)进行update, 和delete这类操做时,原先被标记为删除,可是由于一致性读(consistent read)的关系, 须要保留这些行版本的信息. 可是在full purge 过程当中, innodb存储引擎会判断当前事务中已被删除的行是否能够在表(磁盘)中删除,若是能够,则马上删除. innodb在执行full purge操做时,每次最多尝试回收20个undo page. 最后innodb存储引擎会判断缓冲池中脏页的比例, 若是超过70%, 则刷新100个脏页到磁盘, 若是脏页比例小于70%,则是刷新10%的脏页到磁盘.
background loop :
若当前没有用户活动或者数据库关闭(shutdown)时,就会切换到这个循环. background loop 会执行如下操做.
1 .删除无用的 undo 页(老是)
2. 合并20个插入缓冲页(老是)
3. 跳回到主循环(老是)
4. 不断刷新到100个脏页知道符合条件(可能, 跳转到flush loop 中完成)
若flush loop 中也没有什么事情能够作了, innodb存储引擎会切换到suspend_loop. 将master_thread挂起, 等待事件发生.
若用在mysql中启用了innodb存储引擎,但没有建立innodb表, 则master thread老是处于挂起状态
------------------------------------------------------ 2015-02-10------------------------------------------------------
------------------------------------------------------ 2015-02-11------------------------------------------------------
1.0.x版本以后(1.0.x也进行了修复) , innnodb加入了 innodb_io_capacity 参数用来控制磁盘吞吐量
--按照该值的百分比来控制刷新到磁盘页的数量
1. 在合并插入缓冲时, 合并插入缓冲的数量是该值的5%
2. 在从缓冲中刷新脏页时, 刷新的脏页数量等于该值.
若用户使用了ssd类的磁盘或作了磁盘阵列, 可将该值适当调大.
--1.0.x版本以前,该值默认值为90, 表示缓冲池中脏页占缓冲池的90%. innodb 在每秒刷新缓冲池和flush loop的时候会判断该值,若是脏页所占比例大于该值才刷新100个脏页到磁盘. 仔细想一想90%是否是太大了. 因此在1.0.x版本中. innodb 将该值的默认值改成75.
该值影响每秒刷新脏页的数量. 以前的规则是若是脏页在缓冲池中占比超过 innodb_max_dirty_pages_pct 则执行刷新, 若是没有则不执行刷新. 随着innodb_adaptive_flushing参数的引入.innodb会经过一个名为buf_flush_get_desired_flush_rate函数来判断刷新脏页最合适的数量. 该参数经过判断产生重作日志的速度来决定最合适的刷新脏页数量. 所以当缓冲池中脏页数量小于innodb_max_dirty_pages_pct时,也有可能执行刷新.
该参数控制每次 full purge 回收的 undo 页数量,该参数默认为20. 可动态修改.
不少测试都显示 innodb 1.0.x版本在性能方面获得了极大的提高, 这和 master thread 的改动是密不可分的, 由于innodb 的核心操做大部分集中在 master thread 后台线程中.
执行 show engine innodb status 命令, 以下所示
mysql> show engine innodb status\G; *************************** 1. row *************************** Type: InnoDB Name: Status: ===================================== 150211 16:47:53 INNODB MONITOR OUTPUT ===================================== Per second averages calculated from the last 11 seconds ----------------- BACKGROUND THREAD ----------------- srv_master_thread loops: 56 1_second, 56 sleeps, 5 10_second, 6 background, 6 flush srv_master_thread log flush and writes: 56
......
其中 srv_master_thread loops: 56 表示主循环进行了,56次. 56 sleeps 表示挂起56次, 5 10_second 表示10秒的循环执行了5次. background loop执行6次, flush loop执行6 次.
若是 srv_master_thread loops 与 sleeps 存在较大差距,则代表当前服务器可能很比较繁忙 , 由于innodb在其内部进行了优化, 在压力大的状况下,1秒循环并非每次都sleep .
1.2.x版本中, 将刷新脏页的操做从master thread 分离到一个单独的 page cleaner thread 进程中. 进一步提升了系统的并发性
------------------------------------------------------ 2015-02-11------------------------------------------------------