MySQL系列:innodb源码分析之mini transaction

2024-08-22 08:58

本文主要是介绍MySQL系列:innodb源码分析之mini transaction,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

    日志是innodb一个非常重要的模块,在innodb中有两类日志:redo log和undo log。其中redolog日志是用来做数据异常恢复和数据库重启时页数据同步恢复的,redo log是建立在在mini transaction基础上。数据库在执行事务时,通过minitransaction产生redo log来保证事务的持久性。

1.mini transaction三个协议

        mini-transcation是用来实现innodb的物理逻辑日志的写入和页恢复的,通过mini-transcation来保证并发事务操作和数据库异常是页的一致性。为了得到页的一致性,mini-transaction遵循以下三个协议:

        1. The FIX Rules

      2. Write-Ahead Log

      3. Force-log-at-commit

1.1The FIX Rules

    The FIX Rules规定如下:

              修改一个页需要获得该页的x-latch

              访问一个页是需要获得该页的s-latch或者x-latch

              持有该页的latch直到修改或者访问该页的操作完成

1.2Write-Ahead Log

       Write-Ahead Log的意思就是如果一个页操作在写入到持久设备时,必须内存中相对应的日志写入到持久化设备中。每个页有一个LSN,每次页修改需要维护这个LSN,当一个页需要写入到持久化设备时,要求内存中小于该页LSN的日志先写入到持久化设备中。日志写完后,先Fixed这个页的latch,再将内存中的页刷盘。完成刷盘后,释放页latch。这里遵循The FIX Rules协议。

1.3 Force-log-at-commit

       一个事务可以同时修改了多个页,Write-AheadLog单个数据页的一致性,无法保证事务的持久性。Force -log-at-commit要求当一个事务提交时,其产生所有的mini-transaction日志必须刷到持久设备中。这样即使在页数据刷盘的时候宕机,也可以通过日志进行redo恢复。

2 mini-transaction的日志实现

       innodb是采用mini-transaction来构建操作的物理逻辑日志的,在事务执行的时候,会通过mtr来保证页的数据一致性和持久性。mini-transaction是通过一个mtr_t的结构来实现mini-transaction的三个协议。mtr_t的定义如下:

typedef struct mtr_struct{ulint	 state;                      /*mtr的状态,MTR_ACTIVE、MTR_COMMITING、MTR_COMMITTED*/dyn_array_t	 memo;        /*正在持有的latch列表*/dyn_array_t	 log;             /*mtr产生的日志数据*/ibool	 modifications;     /*是否修改了页*/ulint	 n_log_recs;            /*log操作页的个数*/ulint	 log_mode;             /*log操作模式,MTR_LOG_ALL、MTR_LOG_NONE、MTR_LOG_SHORT_INSERTS*/dulint	 start_lsn;              /*mtr起始的LSN*/dulint  end_lsn;             /*mtr结束的LSN*/ulint  magic_n;             /*魔法字*/}mtr_t;

其中成员memo是个latch持有状态的数组列表,采用的是dyn_array_t的动态内存结构来保存的,每个单元存储的是mtr_memo_slot_t这样的结构。定义如下:
      

typedef struct mtr_memo_slot_struct{ulint	 type;            /*latch的类型值*/void*	 object;        /*latch对象句柄,可以是rw_lock_t或者buf_block_t*/}mtr_memo_slot_t;

latch类型如下:
    MTR_MEMO_PAGE_S_FIX         /*rw_locks-latch*/
    MTR_MEMO_PAGE_X_FIX         /*rw_lockx-latch*/
    MTR_MEMO_BUF_FIX               /*buf_block_t*/
    MTR_MEMO_S_LOCK               /*rw_lock s-latch*/
    MTR_MEMO_X_LOCK               /*rw_lock x-latch*/

 

memo的latch管理接口
    mtr_memo_push                                       获得一个latch,并将状态信息存入mtr memo当中
    mtr_release_s_latch_at_savepoint       释放memo偏移savepoint的slot锁状态
    mtr_memo_contains                          判断锁对象是否在memo当中
    mtr_memo_slot_release                    释放slot锁的控制权
    mtr_memo_pop_all                            释放所有memo中的锁的控制权

mt_t中的log成员是也是一个dyn_array_t动态结构的内存,用来保存mtr产生的日志信息。日志的写入是通过mtr0log.h来写入的。这里指的一提的是日志格式,日志格式是有日志头和日志体组成,日志头信息是由type、space和page no组成,由mlog_write_initial_log_record_fast函数写入到mtr_t的log中的。以下是一个比较具体的示意图:

      

log body的数据写入是通过mtr0log.h中的日志写入方法进行写入的。每写入一跳操作日志,n_log_recs会加1.

标识modifications是标识是否有page的数据改动,如果有,在mtr_commit调用时会先将mtr->log刷盘,然后释放mtr所有的所控制权。日志会一定会在mtr结束时刷盘,这符合Force-log-at-commit的规定。日志写入调用的是log_write_low这个函数。

2.1 mtr_t的内存结构关系图



3 总结

mini transaction是innodb对ACID中的持久性的最小保证单元,所有涉及到事务执行、页数据刷盘、redo log数据恢复等都需要进行mini transaction的构造和执行。几乎所有的模块都涉及到mini transaction,例如:btree、page、事务、inser tbuffer、redo-log等,d对mini transcaion的理解不能孤立的去看源代码,应该结合redo log、page相关的代码了解。它是理解innodb工作原理的基石。



 

 

 

 



这篇关于MySQL系列:innodb源码分析之mini transaction的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/1095821

相关文章

MySQL数据库双机热备的配置方法详解

《MySQL数据库双机热备的配置方法详解》在企业级应用中,数据库的高可用性和数据的安全性是至关重要的,MySQL作为最流行的开源关系型数据库管理系统之一,提供了多种方式来实现高可用性,其中双机热备(M... 目录1. 环境准备1.1 安装mysql1.2 配置MySQL1.2.1 主服务器配置1.2.2 从

Nginx分布式部署流程分析

《Nginx分布式部署流程分析》文章介绍Nginx在分布式部署中的反向代理和负载均衡作用,用于分发请求、减轻服务器压力及解决session共享问题,涵盖配置方法、策略及Java项目应用,并提及分布式事... 目录分布式部署NginxJava中的代理代理分为正向代理和反向代理正向代理反向代理Nginx应用场景

深入理解Mysql OnlineDDL的算法

《深入理解MysqlOnlineDDL的算法》本文主要介绍了讲解MysqlOnlineDDL的算法,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小... 目录一、Online DDL 是什么?二、Online DDL 的三种主要算法2.1COPY(复制法)

Redis中的有序集合zset从使用到原理分析

《Redis中的有序集合zset从使用到原理分析》Redis有序集合(zset)是字符串与分值的有序映射,通过跳跃表和哈希表结合实现高效有序性管理,适用于排行榜、延迟队列等场景,其时间复杂度低,内存占... 目录开篇:排行榜背后的秘密一、zset的基本使用1.1 常用命令1.2 Java客户端示例二、zse

mysql8.0.43使用InnoDB Cluster配置主从复制

《mysql8.0.43使用InnoDBCluster配置主从复制》本文主要介绍了mysql8.0.43使用InnoDBCluster配置主从复制,文中通过示例代码介绍的非常详细,对大家的学习或者... 目录1、配置Hosts解析(所有服务器都要执行)2、安装mysql shell(所有服务器都要执行)3、

Redis中的AOF原理及分析

《Redis中的AOF原理及分析》Redis的AOF通过记录所有写操作命令实现持久化,支持always/everysec/no三种同步策略,重写机制优化文件体积,与RDB结合可平衡数据安全与恢复效率... 目录开篇:从日记本到AOF一、AOF的基本执行流程1. 命令执行与记录2. AOF重写机制二、AOF的

k8s中实现mysql主备过程详解

《k8s中实现mysql主备过程详解》文章讲解了在K8s中使用StatefulSet部署MySQL主备架构,包含NFS安装、storageClass配置、MySQL部署及同步检查步骤,确保主备数据一致... 目录一、k8s中实现mysql主备1.1 环境信息1.2 部署nfs-provisioner1.2.

MySQL中VARCHAR和TEXT的区别小结

《MySQL中VARCHAR和TEXT的区别小结》MySQL中VARCHAR和TEXT用于存储字符串,VARCHAR可变长度存储在行内,适合短文本;TEXT存储在溢出页,适合大文本,下面就来具体的了解... 目录一、VARCHAR 和 TEXT 基本介绍1. VARCHAR2. TEXT二、VARCHAR

MySQL中C接口的实现

《MySQL中C接口的实现》本节内容介绍使用C/C++访问数据库,包括对数据库的增删查改操作,主要是学习一些接口的调用,具有一定的参考价值,感兴趣的可以了解一下... 目录准备mysql库使用mysql库编译文件官方API文档对象的创建和关闭链接数据库下达sql指令select语句前言:本节内容介绍使用C/

mybatis直接执行完整sql及踩坑解决

《mybatis直接执行完整sql及踩坑解决》MyBatis可通过select标签执行动态SQL,DQL用ListLinkedHashMap接收结果,DML用int处理,注意防御SQL注入,优先使用#... 目录myBATiFBNZQs直接执行完整sql及踩坑select语句采用count、insert、u