MySQL 使用元数据锁来管理对数据库对象的并发访问,并确保数据一致性;请参阅 第 10.11.4 节,“元数据锁定”。元数据锁定不仅适用于表,也适用于架构、存储程序(过程、函数、触发器、计划事件)、表空间、使用 GET_LOCK() 函数获取的用户锁(请参阅 第 14.14 节,“锁定函数”),以及使用 第 7.6.9.1 节,“锁定服务” 中所述的锁定服务获取的锁。
Performance Schema 通过 metadata_locks 表公开元数据锁信息
已授予的锁(显示哪些会话拥有哪些当前元数据锁)。
已请求但尚未授予的锁(显示哪些会话正在等待哪些元数据锁)。
死锁检测器已杀死的锁请求。
已超时且正在等待请求会话的锁请求被丢弃的锁请求。
此信息使您可以了解会话之间的元数据锁依赖关系。您不仅可以看到一个会话正在等待哪个锁,还可以看到哪个会话当前持有该锁。
metadata_locks 表为只读表,无法更新。它默认情况下会自动调整大小;要配置表大小,请在服务器启动时设置 performance_schema_max_metadata_locks 系统变量。
元数据锁检测使用 wait/lock/metadata/sql/mdl 仪器,该仪器默认情况下已启用。
要在服务器启动时控制元数据锁检测状态,请在您的 my.cnf 文件中使用类似以下内容的行
启用
[mysqld] performance-schema-instrument='wait/lock/metadata/sql/mdl=ON'禁用
[mysqld] performance-schema-instrument='wait/lock/metadata/sql/mdl=OFF'
要在运行时控制元数据锁检测状态,请更新 setup_instruments 表
启用
UPDATE performance_schema.setup_instruments SET ENABLED = 'YES', TIMED = 'YES' WHERE NAME = 'wait/lock/metadata/sql/mdl';禁用
UPDATE performance_schema.setup_instruments SET ENABLED = 'NO', TIMED = 'NO' WHERE NAME = 'wait/lock/metadata/sql/mdl';
Performance Schema 使用 LOCK_STATUS 列来指示每个锁的状态,如下所示维护 metadata_locks 表内容
当元数据锁被请求并立即获得时,将插入一个状态为
GRANTED的行。当元数据锁被请求但没有立即获得时,将插入一个状态为
PENDING的行。当先前请求的元数据锁被授予时,其行的状态将更新为
GRANTED。当元数据锁被释放时,其行将被删除。
当死锁检测器取消先前请求的挂起锁请求以打破死锁 (
ER_LOCK_DEADLOCK) 时,其行的状态将从PENDING更新为VICTIM。当挂起锁请求超时 (
ER_LOCK_WAIT_TIMEOUT) 时,其行的状态将从PENDING更新为TIMEOUT。当授予的锁或挂起的锁请求被杀死时,其行的状态将从
GRANTED或PENDING更新为KILLED。VICTIM、TIMEOUT和KILLED状态值很短暂,表示锁行即将被删除。PRE_ACQUIRE_NOTIFY和POST_RELEASE_NOTIFY状态值很短暂,表示元数据锁定子子系统在进入锁获取操作或离开锁释放操作时,正在通知感兴趣的存储引擎。
metadata_locks 表具有以下列
OBJECT_TYPE元数据锁子系统中使用的锁类型。该值可以是以下之一:
GLOBAL、SCHEMA、TABLE、FUNCTION、PROCEDURE、TRIGGER(当前未使用)、EVENT、COMMIT、USER LEVEL LOCK、TABLESPACE、BACKUP LOCK或LOCKING SERVICE。值
USER LEVEL LOCK表示使用GET_LOCK()获取的锁。值LOCKING SERVICE表示使用第 7.6.9.1 节,“锁服务”中描述的锁服务获取的锁。OBJECT_SCHEMA包含该对象的模式。
OBJECT_NAME被监控对象的名称。
OBJECT_INSTANCE_BEGIN被监控对象在内存中的地址。
LOCK_TYPE元数据锁子系统中的锁类型。该值可以是以下之一:
INTENTION_EXCLUSIVE、SHARED、SHARED_HIGH_PRIO、SHARED_READ、SHARED_WRITE、SHARED_UPGRADABLE、SHARED_NO_WRITE、SHARED_NO_READ_WRITE或EXCLUSIVE。LOCK_DURATION元数据锁子系统中的锁持续时间。该值可以是以下之一:
STATEMENT、TRANSACTION或EXPLICIT。值STATEMENT和TRANSACTION分别表示在语句或事务结束时隐式释放的锁。值EXPLICIT表示在语句或事务结束时仍然存在并通过显式操作(例如,使用FLUSH TABLES WITH READ LOCK获取的全局锁)释放的锁。LOCK_STATUS元数据锁子系统中的锁状态。该值可以是以下之一:
PENDING、GRANTED、VICTIM、TIMEOUT、KILLED、PRE_ACQUIRE_NOTIFY或POST_RELEASE_NOTIFY。Performance Schema 按前面描述的方式分配这些值。SOURCE包含生成该事件的被监控代码的源文件名称以及在该文件中发生监控的代码行号。这使您能够检查源代码以确定到底涉及哪些代码。
OWNER_THREAD_ID请求元数据锁的线程。
OWNER_EVENT_ID请求元数据锁的事件。
metadata_locks 表具有以下索引
主键为(
OBJECT_INSTANCE_BEGIN)索引为(
OBJECT_TYPE,OBJECT_SCHEMA,OBJECT_NAME)索引为(
OWNER_THREAD_ID,OWNER_EVENT_ID)
不允许对metadata_locks 表执行TRUNCATE TABLE。