3

我在检查Shellshock漏洞时得到了这个:

host1:~$ env x='(){ :;}; echo vulnerable' bash -c "echo hello"
hello
host1:~$ env x='() { :;}; echo vulnerable' bash -c "echo hello"
vulnerable
hello
host1:~$

很奇怪吧?

4

2 回答 2

12

() {如果环境变量恰好以四个字符(包括空格)开头,则 Bash 将环境变量识别为函数。所以env x='(){ :;}; echo vulnerable'不算。

这不太符合您在bash;中定义函数时使用的语法。在内部,bash将以标准化形式存储函数的字符串表示形式。如果函数被导出(带有export -f function_name),那么规范化的形式会被添加到环境中,并且子bash进程会将其识别为函数定义。

“shellshock”错误来自bash处理识别功能的方式;有缺陷的版本bash(可以追溯到很久以前)只是将环境中的字符串评估为函数定义(通过将变量的名称作为函数名称的前缀),这会受到漏洞测试中所示的注入攻击.

手动创建看起来像bash函数定义的字符串以便在子bash进程中定义函数是一种已知技术。导出函数并重新导入它们是很常见的,甚至常常不会被用户注意到。(例如,此技术用于将 bash 函数传递到以xargs bash -c和开头的子shell find ... -exec bash -c。)

于 2014-09-25T16:46:20.990 回答
2

bash对它认为环境中的嵌入式函数定义有点挑剔。在第一

env x='(){ :;}; echo vulnerable' bash -c "echo hello"}

()和之间没有空格{足以防止bash将其识别为导出函数,因此它仍然是一个简单的 shell 变量;看,尝试运行

env x='(){ :;}; echo vulnerable' bash -c 'echo $x'

在第二个示例中x带有空格的 的值被正确地制作以模仿导出的函数,因此孩子bash评估整个值x以“导入”函数,但也执行函数定义之后的代码。

于 2014-09-25T16:44:56.933 回答