怎么理解PostgreSQL Locks中的Lock Manager Internal Locking
本篇内容主要讲解“怎么理解PostgreSQL Locks中的Lock Manager Internal Locking”,感兴趣的朋友不妨来看看。本文介绍的方法操作简单快捷,实用性强。下面就让小编来带大家学习“怎么理解PostgreSQL Locks中的Lock Manager Internal Locking”吧!
一、Lock Manager Internal LockingLockManagerInternalLocking-----------------------------内部锁机制BeforePostgreSQL8.2,alloftheshared-memorydatastructuresusedbythelockmanagerwereprotectedbyasingleLWLock,theLockMgrLock;anyoperationinvolvingthesedatastructureshadtoexclusivelylockLockMgrLock.Nottoosurprisingly,thisbecameacontentionbottleneck.Toreducecontention,thelockmanager'sdatastructureshavebeensplitintomultiple"partitions",eachprotectedbyanindependentLWLock.Mostoperationsonlyneedtolockthesinglepartitiontheyareworkingin.Herearethedetails:在PG8.2或更旧的版本中,共享缓存中的数据结构通过一个单一的LWLock(LockMgrLock)保护;涉及这些数据结构的所有操作必须持有LockMgrLock独占锁.不用说太多,这会成为争用的瓶颈.为了减少争用,锁管理器数据结构已拆分为多个"partitions",每一个分区使用独立的LWLock保护.大多数操作只需要锁定其中一个分区,下面是实现细节:*EachpossiblelockisassignedtoonepartitionaccordingtoahashofitsLOCKTAGvalue.Thepartition'sLWLockisconsideredtoprotectalltheLOCKobjectsofthatpartitionaswellastheirsubsidiaryPROCLOCKs.*只需要授予属于LOCKTAG哈希值的某个分区的锁,分区的LWLock用于保护该分区的所有LOCK对象.*Theshared-memoryhashtablesforLOCKsandPROCLOCKsareorganizedsothatdifferentpartitionsusedifferenthashchains,andthusthereisnoconflictinworkingwithobjectsindifferentpartitions.Thisissupporteddirectlybydynahash.c's"partitionedtable"mechanismfortheLOCKtable:weneedonlyensurethatthepartitionnumberistakenfromthelow-orderbitsofthedynahashhashvaluefortheLOCKTAG.TomakeitworkforPROCLOCKs,wehavetoensurethataPROCLOCK'shashvaluehasthesamelow-orderbitsasitsassociatedLOCK.Thisrequiresaspecializedhashfunction(seeproclock_hash).LOCKs和PROCLOCKs被组织为存储在共享内存中哈希表以便不同的分区使用不同的哈希链,这样不同分区中的对象就不会出现冲突,通过dynahash.c's"partitionedtable"机制实现.只需要确保分区号从LOCKTAG的dynahash哈希值的低位中获取即可.对于PROCLOCKs,必须确保PROCLOCK的哈希值有与LOCK有相同的低位.这需要特别的哈希函数(proclock_hash)*Formerly,eachPGPROChadasinglelistofPROCLOCKsbelongingtoit.Thishasnowbeensplitintoper-partitionlists,sothataccesstoaparticularPROCLOCKlistcanbeprotectedbytheassociatedpartition'sLWLock.(Thisruleallowsonebackendtomanipulateanotherbackend'sPROCLOCKlists,whichwasnotoriginallynecessarybutisnowrequiredinconnectionwithfast-pathlocking;seebelow.)以前的做法,每一个PGPROC都有一个单独的PROCLOCKs链表.现在已拆分为每一个分区一个链表,这样的好处是访问一个PROCLOCK链表可通过相关的分区LWLock保护.(这个规则允许一个后台进程可管理另外一个后台进程的PROCLOCK链表,这个事情本来是不需要做的,但现在在使用fast-path锁的连接时需要)*Theotherlock-relatedfieldsofaPGPROCareonlyinterestingwhenthePGPROCiswaitingforalock,soweconsiderthattheyareprotectedbythepartitionLWLockoftheawaitedlock.PGPROC中与锁相关的域只在PRPROC等待锁才会变得有用,因此我们考虑通过分区LWLOCK中awaitedlock来进行保护.Fornormallockacquisitionandrelease,itissufficienttolockthepartitioncontainingthedesiredlock.Deadlockcheckingneedstotouchmultiplepartitionsingeneral;forsimplicity,wejustmakeitlockallthepartitionsinpartition-numberorder.(TopreventLWLockdeadlock,weestablishtherulethatanybackendneedingtolockmorethanonepartitionatoncemustlocktheminpartition-numberorder.)It'spossiblethatdeadlockcheckingcouldbedonewithouttouchingeverypartitionintypicalcases,butsinceinaproperlyfunctioningsystemdeadlockcheckingshouldnotoccuroftenenoughtobeperformance-critical,tryingtomakethisworkdoesnotseemaproductiveuseofeffort.对于普通的锁请求和释放,锁定包含目标锁的分区就已经足够了.通常来说,死锁检测需要访问多个分区.简单来说,我们只要按分区顺序锁定相关的所有分区即可.(为了避免LWLock死锁,设定的规则是所有需要锁定一个以上分区的后台进程必须一次过按顺序所有所有分区)在典型情况下,不需要访问每一个分区进行死锁检测是可以做到的,但因为在一个正常运行的系统中,死锁检测不应经常发生,因此不会对性能造成较大的影响.Abackend'sinternalLOCALLOCKhashtableisnotpartitioned.WedostoreacopyofthelocktaghashcodeinLOCALLOCKtableentries,fromwhichthepartitionnumbercanbecomputed,butthisisastraightspeed-for-spacetradeoff:wecouldinsteadrecalculatethepartitionnumberfromtheLOCKTAGwhenneeded.后台进程的内部LOCALLOCK哈希表没有分区.我们确实在LOCALLOCK表条目中存储了locktag哈希值的副本,分区号可以计算,这是一个以空间换时间的考量:我们可以从LOCKTAG重新计算分区号.
到此,相信大家对“怎么理解PostgreSQL Locks中的Lock Manager Internal Locking”有了更深的了解,不妨来实际操作一番吧!这里是亿速云网站,更多相关内容可以进入相关频道进行查询,关注我们,继续学习!
声明:本站所有文章资源内容,如无特殊说明或标注,均为采集网络资源。如若本站内容侵犯了原著者的合法权益,可联系本站删除。