performance_schema 默认不显示内存使用是因为内存监控需同时启用 performance_schema 本身和 memory instruments 两级开关;若仅开启前者而未在配置文件中设置 performance-schema-instrument='memory/%=on' 并重启,memory_summary_global_by_event_name 表将为空。

performance_schema 为什么默认不显示内存使用?
MySQL 的 performance_schema 默认关闭内存监控,即使启用也只收集部分事件——memory_summary_global_by_event_name 表为空,不是 bug,是配置未打开。核心开关是 performance_schema 自身 + 内存仪器(instruments)两级控制,缺一不可。
检查当前状态:
SELECT VARIABLE_VALUE FROM performance_schema.global_variables WHERE VARIABLE_NAME = 'performance_schema';
若返回
OFF,重启前必须在配置文件中设为 ON;若已是 ON,但查不到内存数据,说明内存仪器没开。如何启用 memory instruments 并验证生效?
内存统计依赖 memory/sql/*、memory/innodb/* 等 instruments,它们默认全关。需在 MySQL 启动前通过配置文件开启:
- 编辑
my.cnf或my.ini,在[mysqld]下添加:performance-schema-instrument='memory/%=ON'
- 重启 MySQL(仅
SET GLOBAL无法动态开启 memory instruments) - 验证是否加载成功:
SELECT * FROM performance_schema.setup_instruments WHERE NAME LIKE 'memory/%' AND ENABLED = 'YES' LIMIT 5;
至少应看到几十行返回,而非空结果
查内存占用:用哪张表?怎么看关键指标?
启用后,主查 performance_schema.memory_summary_global_by_event_name。注意它统计的是「累计分配量」,不是实时 RSS,但能反映模块级内存倾向:
-
CURRENT_NUMBER_OF_BYTES_USED:当前被该事件类型持有的字节数(最接近“当前占用”) -
CURRENT_NUMBER_OF_ALLOCATIONS:当前活跃分配次数 -
TOTAL_NUMBER_OF_BYTES_ALLOCATED:历史总分配量(含已释放)
常用查询示例:
SELECT EVENT_NAME, CURRENT_NUMBER_OF_BYTES_USED, CURRENT_NUMBER_OF_ALLOCATIONS<br>FROM performance_schema.memory_summary_global_by_event_name<br>WHERE CURRENT_NUMBER_OF_BYTES_USED > 0<br>ORDER BY CURRENT_NUMBER_OF_BYTES_USED DESC<br>LIMIT 10;
重点关注
memory/innodb/buf_buf_pool(Buffer Pool)、memory/sql/Query_cache(若启用)、memory/sql/THD(每个连接的线程结构体)等。为什么查不到 Buffer Pool 实际内存?还有哪些坑?
performance_schema 中的 memory/innodb/buf_buf_pool 只统计 InnoDB 内部 malloc 分配的元数据开销,**不包含 Buffer Pool 本身占用的物理内存**——后者由 innodb_buffer_pool_size 配置项直接决定,且通常通过系统级工具(如 ps aux --sort=-%mem | head -n 10)观察更准。
其他常见盲区:
- InnoDB 的额外内存(如 log buffer、adaptive hash index)不走 performance_schema 内存仪器,需查
SHOW ENGINE INNODB STATUS中的Buffer pool和LOG段 - query cache、host cache、table definition cache 等独立参数控制的内存池,不在 memory instruments 覆盖范围内
- MySQL 8.0.16+ 才支持
memory/performance_schema/*类仪器,旧版本即使开memory/%=ON也无效
真正想看进程级内存,别只盯 performance_schema——它擅长定位“谁在频繁 malloc”,而不是“整个 mysqld 占了多少 RAM”。











