数据库提权中的字符集挑战 - 深度解析与解决方案
前言
在数据库渗透测试中,成功获取数据库权限后,下一步往往是通过数据库提权来执行系统命令,进而获得更高级别的系统访问权限。然而,在这个过程中字符集兼容性问题经常被忽视,导致命令执行失败或结果解析错误。本文以Windows中文环境下MSSQL和MySQL两种数据库提权为案例,深入分析字符集问题及其解决方案。
数据库提权调用机制
无论是MSSQL还是MySQL,当通过数据库执行系统命令时,实际上都是在调用操作系统的命令行接口。在中文Windows系统环境下,提权调用了cmd.exe。
Windows命令行字符集
查询命令行解释器的字符集:
chcp
代码页936表示简体中文(GB2312)
在中文Windows系统环境下,cmd.exe默认使用GBK字符集进行输入输出处理,这意味着:
- 从数据库传递给cmd的命令参数必须是GBK编码
- cmd执行结果的输出也是GBK编码
- 如果字符集不匹配,就会出现乱码或命令执行失败
MSSQL提权中的字符集问题
环境背景
典型场景:针对基于IIS + ASP.NET + MSSQL架构的Web应用进行渗透测试时,发现存在SQL注入漏洞:
- 注入类型:布尔盲注、堆叠注入
- 环境限制:不出网、仅暴露80/443端口
- 权限状况:数据库用户为sysadmin,执行命令权限为nt authority\system
- 系统环境:中文Windows Server
常见问题与解决方案
问题1:寻找网站根路径中文路径的乱码问题
现象:包含中文路径的配置无法正确显示,返回的结果出现乱码。
原因:applicationHost.config文件使用UTF-8编码保存,但CMD使用GBK字符集解码,导致中文字符显示为乱码。
解决方案:
- 使用CyberChef等工具,通过"Encode text" → "Encode text"的recipe来恢复正确的中文字符
- 使用十六进制转换方法获取路径
问题2:盲注中的非ASCII字符处理
在SQL Server中,ASCII()函数无法正确处理非ASCII字符。
解决方案1 - 使用UNICODE函数:
UNICODE(N'中') -- 返回正确的中文字符码位
NCHAR(20013) -- 恢复为中文字符
解决方案2 - 十六进制转换:
- 将中文字符转换为十六进制
- 通过盲注逐个字节读取
- 使用CyberChef恢复原始字符
问题3:sqlmap os-shell的字符集问题
现象:使用sqlmap的os-shell功能时,包含中文的命令会执行失败。
原因:SQLMAP的os-shell会自动将命令使用UTF8编码,并直接输入xp_cmdshell,但CMD使用GBK解码导致乱码。
解决方案:
- 遇到包含中文的命令时,改用sqlmap的sql-shell直接执行
- 使用代理参数分析流量:
--proxy http://127.0.0.1:8080
MySQL UDF提权中的字符集问题
输出结果编码错误
现象:在中文Windows环境下MySQL UDF提权中,执行结果的编码不正确。
解决方案:
在UDF函数外加一层编码转化的函数,确保输出结果使用正确的字符集。
命令中的非ASCII字符处理
现象:当命令参数包含中文时,由于MySQL输入会根据默认字符集(utf8mb4/latin1)编码对应的命令进入命令行解释器,导致执行失败。
解决方案1 - 十六进制编码:
- 使用CyberChef将命令转换为对应编码的十六进制
- 使用十六进制替代原有的字符串
解决方案2 - 编码函数:
利用MySQL的编码转化函数处理命令中的中文字符,确保正确传递到命令行解释器。
总结
- 字符集问题在数据库渗透测试中往往被忽视,在Windows环境下应当格外注意
- MSSQL提权中,中文路径和命令参数需要特殊处理,避免因编码问题导致执行失败
- MySQL UDF提权中,输出结果和命令参数都需要考虑字符集转换
- 工具如sqlmap在使用时需要注意其默认编码行为,必要时绕过工具直接执行命令
- CyberChef等编码转换工具在解决字符集问题时非常有用
参考资料
- MSSQL高权限注入写马至中文路径
- Windows命令行字符集文档
- MySQL字符集处理函数文档
- SQL Server Unicode函数文档