A remotely exploitable hole in bash
A remotely exploitable hole in bash
Posted Sep 25, 2014 15:24 UTC (Thu) by bronson (subscriber, #4806)In reply to: A remotely exploitable hole in bash by jem
Parent article: A remotely exploitable hole in bash
Posted Sep 25, 2014 15:28 UTC (Thu)
by thedevil (guest, #32913)
[Link] (16 responses)
If "sounds dangerous" was a reason not to use something, I don't think I'd be typing this now on my computer ...
Posted Sep 25, 2014 15:48 UTC (Thu)
by cortana (subscriber, #24596)
[Link] (1 responses)
Posted Sep 25, 2014 15:57 UTC (Thu)
by cortana (subscriber, #24596)
[Link]
> curl -H 'foo: () { evil; }' http://foo.example/cgi-bin/somebashscript
Now somebashscript has an attacker-supplied shell function, HTTP_foo. I am deeply uncomfortable with the fact that the script is only one typo away from running it. I would prefer this feature to be ripped out entirely, or at least disabled unless a script runs 'shopt -p terrifying_code_injection'.
Posted Sep 25, 2014 15:51 UTC (Thu)
by foom (subscriber, #14868)
[Link] (8 responses)
If one actually WANTS to eval code from an env var, it's trivial to do so, either by setting BASH_ENV to point to a file you want run, or by starting your subscript with a call to 'eval "$BASH_EVAL_ME_FIRST"'. There's no need for it to be part of bash at all.
I'd really vote for simply killing this misguided "export -f" feature entirely.
But if not, the best way to implement this feature is probably to have bash itself call 'eval "$BASH_EVAL_ME_FIRST"' at startup, and have "export -f" simply append all exported functions into a shell script fragment in that one variable.
Then at least it's clear that allowing that variable to be set allows arbitrary code execution (like BASH_ENV being set to a filename does). Don't need to worry about parser vulnerabilities, or potentially overriding existing functions/binaries.
And it's unlikely that remote users will be able to set such a varible.
Posted Sep 25, 2014 16:21 UTC (Thu)
by gb (subscriber, #58328)
[Link] (7 responses)
$ export A='() { echo "My func"; }'
Thus make me think that way of the storage is implementation detail and it _may be_ backdoor since day 1 15 years ago.
Posted Sep 25, 2014 17:43 UTC (Thu)
by gb (subscriber, #58328)
[Link] (5 responses)
$ cat /proc/$$/environ |xargs -0 -n1|grep -w A
$ env|grep -w A
Means that if someone sets such function in HTTP or something.. you would never see it if you just do $ABCD, only if you do env|grep ABCD
Posted Sep 25, 2014 17:52 UTC (Thu)
by gb (subscriber, #58328)
[Link] (2 responses)
Posted Sep 25, 2014 18:15 UTC (Thu)
by madscientist (subscriber, #16861)
[Link] (1 responses)
The typical functional API to the environment provided by C and other languages treats the environment as a set of key/value pairs, so using those functions it's usually not possible to have two variables with the same name. But, if you start a program with execve() for example you give your own list of strings as the environment for the child process, and the members of that list can be whatever you want.
Posted Sep 25, 2014 20:31 UTC (Thu)
by gb (subscriber, #58328)
[Link]
Posted Sep 26, 2014 11:05 UTC (Fri)
by marcH (subscriber, #57642)
[Link] (1 responses)
Just found this in the standard:
http://pubs.opengroup.org/onlinepubs/7908799/xbd/envvar.html
"If more than one string in a process' environment has the same name the consequences are undefined."
Posted Sep 26, 2014 14:15 UTC (Fri)
by gb (subscriber, #58328)
[Link]
Posted Sep 29, 2014 10:34 UTC (Mon)
by nye (subscriber, #51576)
[Link]
$type A
>Thus make me think that way of the storage is implementation detail
Almost certainly. This behaviour looks exactly like if the function had been defined in the subshell in the traditional way - functions aren't variables, so variable substitution isn't a meaningful thing to do, but 'type' knows exactly what's up, and so does 'set'.
The implementation leaks slightly though, in that the definition is visible in the environment unlike a locally defined function.
Posted Sep 26, 2014 16:32 UTC (Fri)
by bronson (subscriber, #4806)
[Link] (4 responses)
http://seclists.org/oss-sec/2014/q3/741
I don't see any way the benefit of the feature can outweigh all this effort.
Posted Sep 26, 2014 16:59 UTC (Fri)
by raven667 (subscriber, #5198)
[Link] (3 responses)
This is an instance of what is a hard and fast rule in the kernel, "Don't Break Userspace(tm)" It doesn't matter how dumb the feature is in retrospect, it has to continue working even after you refactor the implementation, someone out there could be depending on it, probably without even being aware of it.
Posted Sep 27, 2014 23:28 UTC (Sat)
by bronson (subscriber, #4806)
[Link] (2 responses)
Posted Sep 28, 2014 4:25 UTC (Sun)
by raven667 (subscriber, #5198)
[Link] (1 responses)
Posted Sep 28, 2014 7:25 UTC (Sun)
by bronson (subscriber, #4806)
[Link]
Linux's backward compatibility is nothing short of stellar. It's part of what makes using Linux such a pleasure. But, on the rare occasion that a mistake is made, we don't have to live with it forever. It can be fixed.
A remotely exploitable hole in bash
A remotely exploitable hole in bash
A remotely exploitable hole in bash
A remotely exploitable hole in bash
A remotely exploitable hole in bash
$ bash
$ A
My func
$ echo $A
[nothing here]
$ bash
$ A
My func [still???]
$ export A=3
$ bash
$ A
My func
$ echo $A
3
And how does bash passed both A and My func to subshell here?
A remotely exploitable hole in bash
A=() { echo "My func"
A=3
A=() { echo "My func"
A remotely exploitable hole in bash
A remotely exploitable hole in bash
A remotely exploitable hole in bash
A remotely exploitable hole in bash
A remotely exploitable hole in bash
$ bash
$ f() { aaa; }
$ export -f f
$ export f=3
$ ksh
$ cat /proc/$$/environ |xargs -0 -n1|grep -w f
f=3
f=() { aaa
$ echo $f
3
A remotely exploitable hole in bash
>$ bash
>$ A
>My func
>$ echo $A
>[nothing here]
A is a function
A ()
{
echo "My func"
}
A remotely exploitable hole in bash
A remotely exploitable hole in bash
A remotely exploitable hole in bash
A remotely exploitable hole in bash
A remotely exploitable hole in bash