作家
登录

MySQL引擎特性:InnoDB同步机制

作者: 来源: 2017-12-15 11:37:56 阅读 我要评论

  •  
  •         to wake up possible hanging threads if                                                                                 
  •  
  •         they are missed in mutex_signal_object. */ 
  •  
  •   
  •  
  • if (mutex->waiter != 0) { 
  •  
  •      mutex->waiter = 0; 
  •  
  •      os_event_set(mutex->event); 
  •  
  • 与InnoDB自旋互斥锁的lock_word不合,rw_lock_t中的lock_word是int 型,留意不是unsigned的,其取值范围是(-2X_LOCK_DECR, X_LOCK_DECR],个中X_LOCK_DECR为0x00100000,差不多100多W的一个数。在InnoDB自旋互斥锁互斥锁中,lock_word的取值范围只有0,1,因为这两个状况就能把互斥锁的所有状况都表示出来了,也就是说,只须要查看一下这个lock_word就能肯定当前的线程是否能获得锁。rw_lock_t中的lock_word也扮演了雷同的角色,只须要查看一下当前的lock_word落在哪个取值范围中,就肯定当前哨程可否获得锁。至于rw_lock_t中的lock_word是若何做到这一点的,这其实是InnoDB读写锁甚至InnoDB同步机制中最神奇的处所,下文我们会具体分析。

    InnoDB针对不合的操作体系以及编译器情况,本身封装了一套原子操作,在头文件os0sync.h中。下面的操作基于Linux x86 64位情况, gcc 4.1以上的版本进行分析。

    os_compare_and_swap_xxx(ptr, old_val, new_val)类型的操作底层都应用了gcc包装的__sync_bool_compare_and_swap(ptr, old_val, new_val)函数,语义为,交换成功则返回true,ptr是交换后的值,old_val是之前的值,new_val是交换后的预期值。这个原子操作是个内存樊篱(full memory barrier)。

    os_atomic_increment_xxx类型的操作底层应用了函数__sync_add_and_fetch,os_atomic_decrement_xxx类型的操作应用了函数__sync_sub_and_fetch,分别表示原子递增和原子递减。这个两个原子操作也都是内存樊篱(full memory barrier)。

    别的一个比较重要的原子操作是os_atomic_test_and_set_byte(ptr, new_val),这个操作应用了__sync_lock_test_and_set(ptr, new_val)这个函数,语义为,把ptr设置为new_val,同时返回旧的值。这个操作供给了原子改变某个变量值的操作,InnoDB锁实现的同步机制中,大年夜量的用了这个操作,是以比较重要。须要留意的是,参看gcc文档,这个操作不是full memory barrier,只是一个acquire barrier,简单的说就是,代码中__sync_lock_test_and_set之后操作不克不及被乱序或者重排到__sync_lock_test_and_set之前,然则__sync_lock_test_and_set之前的操作可能被重排到其之后。

    关于内存樊篱的专门指令,MySQL 5.7供给的比较完美。os_rmb表示acquire barrier,os_wmb表示release barrier。如不雅在编程时,须要在某个地位精确的攫取一个变量的值瓯,记得在攫取之前加上os_rmb,同理,如不雅须要在某个地位包管一个变量已经被写了,记得在写之后调用os_wmb。

    前提通知机制

    前提通知机制在多线程协作中异常有效,一个线程往往须要等待其他线程完成指定工作后,再进行工作,这个时刻就须要有线程等待和线程通知机制。Pthread_cond_XXX类似的变量和函数来完成等待和通知的工作。InnoDB中,对Pthread库进行了简单的封装,并在此基本上,进一步抽象,供给了一套便利易用的接口函数给调用者应用。

    体系前提变量

    在文件os0sync.cc中,os_cond_XXX类似的函数就是InnoDB对Pthread库的封装。常用的几个函数如:

    os_cond_t是核心的操尴尬刁难象,其实就是pthread_cond_t的一层typedef罢了,os_cond_init初始化函数,os_cond_destroy烧毁函数,os_cond_wait前提等待,不会超时,os_cond_wait_timed前提等待,如不雅超时则返回,os_cond_broadcast唤醒所有等待线程,os_cond_signal只唤醒个一一个等待线程,然则在浏览源码的时刻发明,似乎没有什么处所调用了os_cond_signal。。。

    此外,还有一个os_cond_module_init函数,用来window下的初始化操作。

    event是一个InnoDB前提变量,当当前的锁已经被一个线程以写锁方法独有时,后续的读锁和写锁都等待在这个event上,当这个线忱矸⑴写锁时,等待在这个event上的所有读锁和写锁同时竞争。waiters这变量,与event一路用,当有等待者在等待时,这个变量被设置为1,不然为0,锁被释放的时刻,须要经由过程这个变量来断定有没有等待者大年夜而履行os_event_set。

    在InnoDB下,os_cond_XXX模块的函数主如果给InnoDB本身设计的前提变量应用。

    InnoDB前提变量

    如不雅在InnoDB层直接应用体系前提变量的话,重要有四个弊病,起首,弊病1,体系前提变量的应用须要与一个体系互斥锁(详见下一节)相合营应用,应用完还要记得及时释放,应用者会比较麻烦。接着,弊病2,在前提等待的时刻,须要在一个轮回中等待,应用者照样比较麻烦。最后,弊病3,也是比较重要的,不便利体系监控。


      推荐阅读

      海尔王养浩:让IT成为业务和创新的赋能者

    数字化转型已成为趋势,然而既然是转型则必定会带来阵痛,新技巧在带来新的颠覆的同时,也给IT运维治理带来新的挑衅,包含稳定性、扩大性、灵活性、成本、投资回报率等等。对于IT治理者而言,若何经由过程大年夜数据>>>详细阅读


    本文标题:MySQL引擎特性:InnoDB同步机制

    地址:http://www.17bianji.com/lsqh/39799.html

    关键词: 探索发现

    乐购科技部分新闻及文章转载自互联网,供读者交流和学习,若有涉及作者版权等问题请及时与我们联系,以便更正、删除或按规定办理。感谢所有提供资讯的网站,欢迎各类媒体与乐购科技进行文章共享合作。

    网友点评
    自媒体专栏

    评论

    热度

    精彩导读
    栏目ID=71的表不存在(操作类型=0)