根本原因是密钥未与ibd文件分离,而是由服务端keyring插件统一管理且弱保护落盘;攻击者获root权限后可直接读取keyring文件或内存密钥,从而解密任意拷走的ibd文件。

ibd 文件被拷走后仍能解密,根本原因不是“文件本身可逆”,而是加密密钥未随数据分离——MySQL 的表空间加密(Data-at-Rest Encryption)默认不绑定密钥到物理文件,密钥由服务端插件(如 keyring_file)统一管理,且密钥明文或弱保护地落盘。
密钥没跟着文件走,但攻击者能拿到它
keyring_file 插件默认把密钥存成纯文本或弱加密格式在磁盘上(例如 /var/lib/mysql-keyring/keyring),路径可被 mysqld 进程读取。一旦攻击者获得服务器 root 权限(比如通过漏洞、弱口令、恶意定时任务),就能:
- 直接读取
keyring文件内容 - 或用
mysql客户端连上本地实例执行SELECT * FROM performance_schema.keyring_keys;(若权限未严格限制) - 甚至通过
gdbattachmysqld进程 dump 内存中的解密密钥
只要密钥在,拷走的 ibd 就能在另一台装好同版本 MySQL + 同 keyring 插件的机器上直接挂载使用。
表空间加密 ≠ 文件自带密钥
MySQL 的 innodb_encrypt_tables=ON 只是启用加密开关,它不生成 per-table 密钥,也不把密钥写进 ibd 头部。所有加密都依赖全局 keyring,而 keyring 的安全性完全取决于:
- 存储位置是否受控(比如放在
/tmp或与数据目录同挂载点 → 危险) - 文件权限是否宽松(
chmod 644 /var/lib/mysql-keyring/keyring→ 可被普通用户读) - 是否启用了
keyring_encrypted_file(需额外配置密码,否则和keyring_file一样裸奔)
拷走文件后解密的典型链路
- 攻击者拿下服务器 shell,发现
mysqld正在运行 → 立刻执行ps aux | grep keyring找 keyring 配置路径 - 读取
my.cnf,确认early-plugin-load=keyring_file.so和keyring_file_data=/var/lib/mysql-keyring/keyring -
cat /var/lib/mysql-keyring/keyring→ 得到密钥明文(base64 编码但无实质保护) - 拷走全部
ibd+frm+keyring文件 → 在本地复原出完整数据库
真正防拷走解密,得打破密钥与数据共存
- 把
keyring_file_data放在独立挂载点、不同用户可读的路径(如/mnt/secure-keyring/keyring),并chown root:root+chmod 600 - 改用
keyring_okv或云 KMS(如 AWS KMS、阿里云 KMS),密钥永不落地,解密请求必须走网络调用 - 若用
keyring_encrypted_file,必须显式设置启动参数--keyring_encrypted_file_password=xxx,且该密码不能写进配置文件(应由运维手动输入或注入环境变量)
密钥管理松散,比加密算法本身更致命。文件拷走不可怕,可怕的是密钥就躺在旁边,还贴了张纸条写着“请解密用”。











