searchusermenu
  • 发布文章
  • 消息中心
点赞
收藏
评论
分享
原创

InnoDB后台线程介绍(一)

2023-08-18 06:50:12
13
0

一、srv_master_thread

文件:srv0srv.cc : srv_master_thread
 

master thread 主要工作(每隔一秒,不绝对一秒,因为下面的工作是串行的):

  • 在后台清理alter table遗留的表,一次清理一张表

  • 检查是否需要刷redo log buffer或做checkpoint, 确保redo log buffer 有足够空间

  • insert buffer merge

  • 刷 redo log buffer 到文件并fsync到磁盘

  • 从table cache 中清除至多50%不使用的表 (server空闲的时候每秒,不空闲的时候每隔一段时间进行一次)

  • 做checkpoint (server空闲的时候每秒,不空闲的时候每隔一段时间进行一次)

代码堆栈如下:

while(!shutdown):                         # 无限循环,直到shutdown
   sleep(1s)                              # 睡眠1秒
   if server is active:                   
       srv_master_do_active_tasks()       # 如果server处于活动状态
    else
       srv_master_do_idle_tasks()         # 如果server处于idle状态

srv_master_do_active_tasks()
|- row_drop_tables_for_mysql_in_background()  # 在后台清理 ALTER TABLE 遗留的表lazy drop,一次操作drop一个表
|- log_free_check()                           # 检查是否需要刷redo log buffer或做checkpoint,确保redo log buffer 有足够空间
|- ibuf_merge_in_background()                 # insert buffer merge
|- srv_sync_log_buffer_in_background()        # flush redo log buffer
|- srv_master_evict_from_table_cache()        # 不是每秒做一次,每隔一段时间,从table cache 中清除至多50%不使用的表缓存
|- log_checkpoint()                           # 不是每秒做一次,每隔一段时间,做checkpoint


srv_master_do_idle_tasks()
|- row_drop_tables_for_mysql_in_background()  # 在后台清理 ALTER TABLE 遗留的表lazy drop
|- log_free_check()                           # 确保redo log文件有足够reusable空间
|- ibuf_merge_in_background()                 # insert buffer merge
|- srv_master_evict_from_table_cache(50)      # 从table cache 中清除至多50%不使用的表
|- srv_sync_log_buffer_in_background          # 刷 redo log buffer 到文件并fsync到磁盘
|- log_checkpoint(TRUE, FALSE)                # 做checkpoint


row_drop_tables_for_mysql_in_background()    # 后台drop 表,一次操作drop一个表
|- UT_LIST_GET_FIRST(row_mysql_drop_list)    # 获取第一个需要drop的表
|- dict_table_open_on_name()                 # 打开第一个drop的表
|- row_drop_table_for_mysql_in_background    # 在后台删除表
|  |- trx_allocate_for_background()          # 分配一个后台事务对象
|  |- row_drop_table_for_mysql()             # 在innodb中删除表
|  |- log_buffer_flush_to_disk()             # redo log 刷盘
|  |- trx_commit_for_mysql()                 # 事务提交
|  |- trx_free_for_background()              # 释放事务对象


log_free_check()                         # 检查是否需要刷redo log buffer或做checkpoint,确保redo log buffer 有足够空间
|- log_check_margins()                   
|  |- log_flush_margin()
|  |  |- buf_free > max_buf_free log_write_up_to(false)  # 刷redo log buffer到文件,不fsync
|  |- log_checkpoint_margin()   


log_free_check()                         # 检查是否需要刷redo log buffer或做checkpoint,确保redo log buffer 有足够空间
|- log_check_margins()                   
|  |- log_flush_margin()
|  |  |- buf_free > max_buf_free log_write_up_to(false)  # 刷redo log buffer到文件,不fsync
|  |- log_checkpoint_margin()   


srv_master_evict_from_table_cache(50)
|- dict_make_room_in_cache(table_definition_cache,50%)  # 从table cache 中清除至多50%不使用的表缓存

二、io_handler_thread

文件:srv0start.cc : io_handler_thread

io thread的主要作用:

  • innodb相关的异步IO操作

线程数量:
srv_n_file_io_threads = read_io_threads + write_io_threads + 2 (log and ibuf IO threads)
线程种类:
    read_io_thread
    write_io_thread
    log io thread
    ibuf io thread

while (srv_shutdown_state != SRV_SHUTDOWN_EXIT_THREADS
	   || buf_page_cleaner_is_active
	   || !os_aio_all_slots_free()) {
	fil_aio_wait(segment);       # Waits for an aio operation to complete
}

三、buf_flush_page_cleaner_worker

文件:buf0flu.cc

page cleaner worker的主要作用:

  • 真正的buffer pool刷脏线程

线程数量:srv_n_page_cleaners = innodb_page_cleaners > innodb_buffer_pool_instance ? innodb_buffer_pool_instance : innodb_page_cleaners

while (true) {
		os_event_wait(page_cleaner->is_requested);
		if (!page_cleaner->is_running) {
			break;
		}
		pc_flush_slot();                 # flush one slot
	}
0条评论
作者已关闭评论
lawen
10文章数
1粉丝数
lawen
10 文章 | 1 粉丝
原创

InnoDB后台线程介绍(一)

2023-08-18 06:50:12
13
0

一、srv_master_thread

文件:srv0srv.cc : srv_master_thread
 

master thread 主要工作(每隔一秒,不绝对一秒,因为下面的工作是串行的):

  • 在后台清理alter table遗留的表,一次清理一张表

  • 检查是否需要刷redo log buffer或做checkpoint, 确保redo log buffer 有足够空间

  • insert buffer merge

  • 刷 redo log buffer 到文件并fsync到磁盘

  • 从table cache 中清除至多50%不使用的表 (server空闲的时候每秒,不空闲的时候每隔一段时间进行一次)

  • 做checkpoint (server空闲的时候每秒,不空闲的时候每隔一段时间进行一次)

代码堆栈如下:

while(!shutdown):                         # 无限循环,直到shutdown
   sleep(1s)                              # 睡眠1秒
   if server is active:                   
       srv_master_do_active_tasks()       # 如果server处于活动状态
    else
       srv_master_do_idle_tasks()         # 如果server处于idle状态

srv_master_do_active_tasks()
|- row_drop_tables_for_mysql_in_background()  # 在后台清理 ALTER TABLE 遗留的表lazy drop,一次操作drop一个表
|- log_free_check()                           # 检查是否需要刷redo log buffer或做checkpoint,确保redo log buffer 有足够空间
|- ibuf_merge_in_background()                 # insert buffer merge
|- srv_sync_log_buffer_in_background()        # flush redo log buffer
|- srv_master_evict_from_table_cache()        # 不是每秒做一次,每隔一段时间,从table cache 中清除至多50%不使用的表缓存
|- log_checkpoint()                           # 不是每秒做一次,每隔一段时间,做checkpoint


srv_master_do_idle_tasks()
|- row_drop_tables_for_mysql_in_background()  # 在后台清理 ALTER TABLE 遗留的表lazy drop
|- log_free_check()                           # 确保redo log文件有足够reusable空间
|- ibuf_merge_in_background()                 # insert buffer merge
|- srv_master_evict_from_table_cache(50)      # 从table cache 中清除至多50%不使用的表
|- srv_sync_log_buffer_in_background          # 刷 redo log buffer 到文件并fsync到磁盘
|- log_checkpoint(TRUE, FALSE)                # 做checkpoint


row_drop_tables_for_mysql_in_background()    # 后台drop 表,一次操作drop一个表
|- UT_LIST_GET_FIRST(row_mysql_drop_list)    # 获取第一个需要drop的表
|- dict_table_open_on_name()                 # 打开第一个drop的表
|- row_drop_table_for_mysql_in_background    # 在后台删除表
|  |- trx_allocate_for_background()          # 分配一个后台事务对象
|  |- row_drop_table_for_mysql()             # 在innodb中删除表
|  |- log_buffer_flush_to_disk()             # redo log 刷盘
|  |- trx_commit_for_mysql()                 # 事务提交
|  |- trx_free_for_background()              # 释放事务对象


log_free_check()                         # 检查是否需要刷redo log buffer或做checkpoint,确保redo log buffer 有足够空间
|- log_check_margins()                   
|  |- log_flush_margin()
|  |  |- buf_free > max_buf_free log_write_up_to(false)  # 刷redo log buffer到文件,不fsync
|  |- log_checkpoint_margin()   


log_free_check()                         # 检查是否需要刷redo log buffer或做checkpoint,确保redo log buffer 有足够空间
|- log_check_margins()                   
|  |- log_flush_margin()
|  |  |- buf_free > max_buf_free log_write_up_to(false)  # 刷redo log buffer到文件,不fsync
|  |- log_checkpoint_margin()   


srv_master_evict_from_table_cache(50)
|- dict_make_room_in_cache(table_definition_cache,50%)  # 从table cache 中清除至多50%不使用的表缓存

二、io_handler_thread

文件:srv0start.cc : io_handler_thread

io thread的主要作用:

  • innodb相关的异步IO操作

线程数量:
srv_n_file_io_threads = read_io_threads + write_io_threads + 2 (log and ibuf IO threads)
线程种类:
    read_io_thread
    write_io_thread
    log io thread
    ibuf io thread

while (srv_shutdown_state != SRV_SHUTDOWN_EXIT_THREADS
	   || buf_page_cleaner_is_active
	   || !os_aio_all_slots_free()) {
	fil_aio_wait(segment);       # Waits for an aio operation to complete
}

三、buf_flush_page_cleaner_worker

文件:buf0flu.cc

page cleaner worker的主要作用:

  • 真正的buffer pool刷脏线程

线程数量:srv_n_page_cleaners = innodb_page_cleaners > innodb_buffer_pool_instance ? innodb_buffer_pool_instance : innodb_page_cleaners

while (true) {
		os_event_wait(page_cleaner->is_requested);
		if (!page_cleaner->is_running) {
			break;
		}
		pc_flush_slot();                 # flush one slot
	}
文章来自个人专栏
MySQL
2 文章 | 1 订阅
0条评论
作者已关闭评论
作者已关闭评论
0
0