Bash-kwetsbaarheid laat aanvaller code uitvoeren op Linux en OS X

Een kwetsbaarheid laat aanvallers code injecteren in de Bash-shell, die door OS X en vrijwel alle Linux-distributies wordt gebruikt. Daardoor zou een aanvaller bijvoorbeeld via een kwetsbaar cgi-script zijn eigen code op een systeem kunnen uitvoeren.

De kwetsbaarheid kan worden misbruikt door een aantal tekens, gevolgd door code, toe te voegen aan een environment-variabele, schrijft Red Hat op zijn beveiligingsblog. Zodra vervolgens een bash-sessie wordt geopend, blijkt die code te worden uitgevoerd.

De bash-shell is in OS X en vrijwel alle Linux-distributies aanwezig en laat de gebruiker via de command-line instructies uitvoeren. Ook software kan de shell gebruiken om instructies uit te voeren. Het op Linux gebaseerde Android is standaard niet kwetsbaar, tenzij een gebruiker zelf bash heeft geïnstalleerd, bijvoorbeeld via een custom rom. Een patch voor de Linux-versie van bash is beschikbaar; voor OS X nog niet. Diverse distrubuties zoals Debian en Ubuntu hebben al een update klaar staan die gebruikers kunnen installeren.

De kwetsbaarheid is op verschillende manieren te misbruiken; bash-shells kunnen bijvoorbeeld worden geopend door een cgi-script. Wanneer een website een cgi-script met een bash-shell gebruikt, is die website dus in potentie kwetsbaar voor het uitvoeren van code.

Beveiligingsonderzoeker Robert Graham noemt de bug in bash 'net zo groot als Heartbleed', een beveiligingsprobleem in OpenSSL waarbij een deel van de inhoud van het interne geheugen van een server kon worden uitgelezen. Dat komt volgens Graham doordat er zoveel verschillende manieren zijn waarop Linux-software interactie vertoont met bash. "We zullen nooit alle software kunnen uitfaseren die kwetsbaar is voor de bash-bug", schrijft hij.

Php-scripts die shell gebruiken zijn niet kwetsbaar, mits de php-scripts via mod_php worden aangeroepen. Dhcp-clients zijn wel kwetsbaar: dhcp-servers zouden in potentie code kunnen injecteren op een systeem, waarbij commando's worden uitgevoerd als root. Dat is bijvoorbeeld een gevaar op openbare wifi-hotspots, mits de gebruiker dus een Linux-distributie met bash gebruikt. Ook de web-interfaces van routers die de mogelijkheid bieden om pings en traceroutes uit te voeren, zijn waarschijnlijk kwetsbaar.

Onderzoeker Graham stelt dat ook apparaten met een eigen webserver aan boord, zoals webcams, kwetsbaar zijn, omdat die vaak leunen op bash-scripts die worden bestuurd via een website. Bovendien is de bug niet alleen aanwezig in recente versies van bash: de bug is al lange tijd aanwezig. "Het aantal systemen dat moet worden gepatcht is daarom vele groter dan bij de Heartbleed-bug", schrijft Graham.

Gebruikers die willen weten of hun systeem kwetsbaar is, kunnen een simpele test uitvoeren door de code env x='() { :;}; echo kwetsbaar' bash -c "echo dit is een test" uit te voeren in een shell. Wordt 'kwetsbaar' getoond, dan is het systeem in kwestie kwetsbaar.

Door Joost Schellevis

Redacteur

24-09-2014 • 20:45

213

Reacties (213)

213
198
144
28
2
31
Wijzig sortering
Anoniem: 490422 25 september 2014 01:58
Het blijkt nog steeds mogelijk om bash te exploiten, zie laatste comment op: https://bugzilla.redhat.com/show_bug.cgi?id=1141597#c23

Je kunt dit zelf controleren door deze line uit te voeren:

env -i X='() { (a)=>\' bash -c 'echo date'; cat echo

bash: X: line 1: syntax error near unexpected token `='
bash: X: line 1: `'
bash: error importing function definition for `X'
Thu Sep 25 01:57:29 CEST 2014

[Reactie gewijzigd door Anoniem: 490422 op 26 juli 2024 08:22]

Ik had eerst niet door wat er nu gebeurde daar. Ik moest meerdere keren de tweet op https://twitter.com/taviso/status/514887394294652929 lezen voordat ik door had dat de side-effect de creatie van een file was.

In ieder geval met:

env X='() { (a)=>\' bash -c "echo ls /; cat echo"
Je kan deze ook eens proberen:
env -i X='() { (a)=>\' bash -c 'echo curl -s https://bugzilla.redhat.com/'; head echo

Dat maakt het misschien wat duidelijker wat er nou gebeurt. :)
vmWare ESXi heeft er ook last van; in elk geval 5.5, maar waarschijnlijk ook eerdere. Ze gebruiken dus waarschijnlijk een gerenamede bash shell als /bin/sh. Nog geen patch beschikbaar; ze geven zelf aan dat het 'in onderzoek' is, en vmWare kennende kost ze dat wel een aantal dagen :(
Ik heb hier ook ESXi 5.5 draaien, maar nergens last van...

% ssh esxhost
Password:
VMware offers supported, powerful system administration tools. Please
see www.vmware.com/go/sysadmintools for details.

The ESXi Shell can be disabled by an administrative user. See the
vSphere Security documentation for more information.

~ # echo $SHELL
/bin/sh

~ # env x='() { :;}; echo kwetsbaar' bash -c "echo dit is een test"
env: can't execute 'bash': No such file or directory

~ # env x='() { :;}; echo kwetsbaar' sh -c "echo dit is een test"
dit is een test
~ #

[Reactie gewijzigd door JackBol op 26 juli 2024 08:22]

Even gekeken; foutje vanaf mijn kant: het betrof de vCenter Appliance - die is wel vatbaar (de Appliance is een SuSe VM):

vcenter:~ # env x='() { :;}; echo vulnerable' bash -c "echo this is a test"
vulnerable
this is a test
vcenter:~ # uname -a
Linux vcenter 3.0.101-0.7.19-default #1 SMP Fri May 9 14:41:39 UTC 2014 (aab30c0) x86_64 x86_64 x86_64 GNU/Linux

De ESXi dozen zijn inderdaad niet vatbaar
Anoniem: 146875 24 september 2014 21:02
Een vervelende bug maar om dit te vergelijken met hearthbleed is overdreven. Het verschil is dat via hearthbleed (eenvoudig) remote code execution mogelijk is. Via deze bash bug is dat niet zo, je moet al iets op een server mogen uitvoeren wil je dit kunnen misbruiken. Je laat niet zo maar gebruikers commando's uitvoeren via een shell, niet via CGI of PHP, als dat kan heb je een veel groter probleem.

Volgens de advisory: "Shell scripts which do not export variables are not vulnerable to this issue, even if they process untrusted content and store it in (unexported) shell variables and open subshells."

Om dan deze bug te vergelijken met hearthbleed gaat te ver.
Nou dan moet je de details nog maar eens goed gaan doorlezen, heartbleed was helemaal geen remote code execution, dit wel, en niet zomaar op 1 manier maar op potentieel honderden manieren
Bijna. Heartbleed was inderdaad geen remote code execution bug, maar lekt wel privé-informatie als (delen van) wachtwoorden en encryptiekeys. Deze bug is echter ook geen "remote code execution".
Wat is aangetoond is dat het mogelijk is in bash om een env variable aan te maken die code bevat, welke vervolgens wordt uitgevoerd elke keer dat bash start. Wat niet is aangetoond is dat je die environment variabele remote kan aanmaken. Daarvoor zal je eerst toegang moeten krijgen tot een (bash) shell, en normaal gesproken heb je dat remote niet. Je hebt dus nog steeds een andere bug nodig. Die laatste zou een een "remote code execution" bug moeten zijn, de "shellshock" bug is slechts een vervelende manier om je payload te triggeren in taken waar je ze niet verwacht mits je remote access hebt.

[Reactie gewijzigd door RSpliet op 26 juli 2024 08:22]

Je gaat hier aan een erg belangrijk punt voorbij, namelijk dat CGI automatisch HTTP headers omzet in environment variables (zoals TrafeX hierboven ook aangeeft). Zo wordt de HTTP host header de variabele REMOTE_HOST, maar je kunt ook custom headers meegeven. Aanvallers kunnen dus zonder enige moeite deze variabeles via CGI remote aanmaken en er is dus geen toegang tot een bash shell nodig.

Aangezien veel simpele webservers gebruik maken van shellscripts via CGI met /bin/sh shebang (/bin/sh linkt regelmatig naar bash), is het dus wel degelijk een serieuze remote code execution vulnerability. Helemaal omdat de HTTP daemon onder root draait op veel embedded systemen (bijv. NAS).
Oef... dat is inderdaad erg naar. Ik ben zelf opgevoed met mod_php, dus zonder CGI. Die zal dus niet vuln zijn. Tnx voor de aanvulling! :-)
Jammer genoeg spreekt men heel generiek over CGI terwijl we meerdere vormen hebben, hoe zit het met de FCGI implementaties en met bijvoorbeeld PHP_FPM.
Hierboven wordt gezegd dat environment variables geen probleem vormen, tenzij ze worden geëxporteerd. Ik ben niet zo bekend met CGI; worden de variabelen (zoals REMOTE_HOST) slechts opgeslagen of ook geëxporteerd?
Helemaal mee eens.
Met Heartbleed was het mogelijk om aan inloggegevens te komen, zonder zelf enige toegang te hebben. Bij deze bug moet je eerst toegang verkrijgen om het environment te kunnen wijzigen.
Software (of systeemconfiguraties) die niet geautoriseerden het environment laten wijzigen zijn zelf ook al dubieus te noemen.

[Reactie gewijzigd door fds op 26 juli 2024 08:22]

Om onder OS X een gefikste bash te draaien kan je brew gebruiken, sinds 2 uur terug.

$ brew update && brew install bash
$ echo "/usr/local/bin/bash" | sudo tee -a /etc/shells
$ chsh -s /usr/local/bin/bash
$ bash
$ bash --version
GNU bash, versie 4.3.25(1)-release (x86_64-apple-darwin13.4.0)
Copyright (C) 2013 Free Software Foundation, Inc.
De licentie is GPLv3+: GNU GPL versie 3 of later.
Zie http://gnu.org/licenses/gpl.html voor de volledige tekst.

Dit is vrije software; u mag het vrijelijk wijzigen en verder verspreiden.
Er is GEEN GARANTIE, voor zover de wet dit toestaat.
$ env x='() { :;}; echo vulnerable' bash -c "echo this is a test"
bash: waarschuwing: x: ignoring function definition attempt
bash: fout tijdens importeren van functiedefinitie voor 'x'
this is a test
$ env x='() { :;}; echo vulnerable' /bin/bash -c "echo this is a test"
vulnerable
this is a test

[Reactie gewijzigd door Henk Poley op 26 juli 2024 08:22]

Maar hoe helpt dit dan? Als je ergens een cgi script hebt draaien gebruikt die wel gewoon /bin/bash, dus dan ben je nog vulnerable? En als je toch al een shell hebt...kun je jezelf ook zonder deze vulnerability in de voet schieten of met de buit ervandoorgaan :)
Klopt. Daarom ook die laatst regel met vette tekst, om aan te tonen dat je nog steeds ergens aan te vallen bent. Dan moet je dus /bin/bash verwijderen en linken naar je nieuwe bash.

Iets als:

$ sudo rm /bin/bash
$ sudo ln /usr/local/bin/bash /bin/bash

En dan nog hetzelfde met /bin/sh, dat ook bash is, iig. onder OS X Mavericks.

Edit: ik heb net brew's bash naar /bin/sh en /bin/bash gekopieerd, en de boel werkt, en m'n systeem reboot verder gewoon. Let wel dat bash in brew nog niet geheel gepatched is.

Overigens vervang je dan je systeem bash door een shell die je zonder root wachtwoord kan overschrijven. De standaard 'brew' installatie is immers geïnstalleerd in een map met jouw eigen rechten. Kan een probleem zijn als je webserver automatisch de rechten aanneemt van het script (set doc root UID mode)

Daarnaast is het probleem in bash nog niet geheel opgelost:
https://twitter.com/taviso/status/514887394294652929

/bin/sh onder OS X (is kopie van bash):
https://twitter.com/jacobwcarlson/status/514913363739303936

zsh, vals alarm?
https://twitter.com/SalmiaknSQL/status/514951032137596928
https://twitter.com/tbaldauf/status/514877616902664192

dash, ook vals alarm ?
https://twitter.com/SalmiaknSQL/status/514948059277819905

Het kan zijn dat die laatste drie meldingen zijn van mensen die niet helemaal door hebben waar het probleem ligt, en per ongeluk gewoon bash aanroepen in die 'echo vulnerable' test. Zit geen 'Proof of Concept' bij.

[Reactie gewijzigd door Henk Poley op 26 juli 2024 08:22]

Valt wel mee hoor. Ik heb maar de helft verteld om /bin/bash ook echt te vervangen :P

Er is overigens inmiddels ook nog een ander probleem gevonden in dezelfde functionaliteit. Die is nog niet gepatched in brew.

https://twitter.com/taviso/status/514887394294652929

[Reactie gewijzigd door Henk Poley op 26 juli 2024 08:22]

Ik vind de hack nogal vergezocht: het heeft een hoog SQL injectie gehalte maar dan via Bash. Als je een variabele kunt zetten dan kun je bash foppen. Als je op dat niveau de machine kunt beinvloeden zou ik gewoon een LD_PRELOAD erin zetten en printf() ondervangen met een eigen versie. Helemaal leuk als iemand su intikt zonder de environment te wipen.
Mensen die bash scripts als cgi inzetten verdienen het gehackt te worden.
Ik denk dat je niet goed begrijpt hoe deze kwetsbaarheid werkt. Allerlei programma's stoppen al allerlei gegevens in environmental variables. Maar natuurlijk niet in variabelen zoals LD_PRELOAD die een speciale betekenis hebben.

Bij het CGI protocol worden bijvoorbeeld door de webserver variabelen als QUERY_STRING en USER_AGENT ingevuld met de gegevens die door de client aangeleverd zijn, zodat het CGI script daar iets mee kan doen. Dat is volledig onschuldig, want een CGI script zal (als het goed is) eventuele code die in die variabelen terecht komt nooit uitvoeren. Dit is dan ook een veel gebruikte manier om data tussen processen uit te wisselen.

Het probleem is nu echter dat de shell die code al uitvoert, ongeacht in welke variabele die staat. Dat betekent dat alle bash scripts die via CGI te benaderen zijn nu al kwetsbaar zijn, ongeacht hoe veilig de scriptcode zelf is. Dat is absoluut niet te vergelijken met een situatie waarin de scriptcode zelf een kwetsbaarheid bevat, of een situatie waarin je als aanvaller variabelen naar keuze (zoals LD_PRELOAD) kunt wijzigen (nog even los van het feit dat je dan ook nog wat kwetsbare code op de host moet zien te krijgen, anders valt er überhaupt niets te preloaden).

[Reactie gewijzigd door Soultaker op 26 juli 2024 08:22]

Dank voor de extra toevoeging maar de eerste ontwikkelaar in mijn team die bash scripts start vanuit een webapp moet ik nog vinden. Vandaar dat ik het nogal vergezocht vind.
Wat wil je daarmee zeggen? Dat omdat jij het niet ziet in jou team dat het niet gebeurt? Er word best wel veel gebruik gemaakt van CGI scripts en al die scripts zijn nu dus kwetsbaar (van de systemen die niet zijn gepatched ofc). Het afdoen als 'Ik heb het nog nooit gezien dus het is vergezocht' is super gevaarlijk in de security wereld.
Anoniem: 428335 @latka24 september 2014 21:52
Vele webservers zetten automatisch bepaalde environment variabelen. Bijvoorbeeld HTTP_USER_AGENT naar de 'User-Agent:' header. Daarmee kan de gebruiker niet de LD_PRELOAD variabele zetten, maar dus door deze bug in bash wel code uitvoeren door als user agent string '() {:;}; <dingen>' te geven.

Het gaat niet alleen om bash scripts trouwens. Het is gebruikelijk dat programma's andere programma's uitvoeren via een shell, wat regelmatig bash is.

[Reactie gewijzigd door Anoniem: 428335 op 26 juli 2024 08:22]

De bash-shell is in OS X, vrijwel alle Linux-distributies en BSD-varianten aanwezig
Dit is niet helemaal correct. Op zowel FreeBSD als OpenBSD is standaard geen bash shell aanwezig.
bash is een populaire shell, de default op de meeste Linux distributies, en wordt daarom ook veel gebruikt op bijvoorbeeld BSDs. Maar op mijn server met FreeBSD is bijvoorbeeld geen bash aanwezig. Dat staat er standaard immers niet op.
En dan nog loopt alles standaard in sh wat via ports is geïnstalleerd.

edit: oh wacht je kunt natuurlijk het command aanroepen via bash -c :+

edit2: ports tree is ook al lang aangepast. Dus user zijn zelf verantwoordelijk voor het patchen omdat bash geen deel uitmaakt van FreeBSD

[Reactie gewijzigd door matty___ op 26 juli 2024 08:22]

En dan nog loopt alles standaard in sh wat via ports is geïnstalleerd.

/bin/sh (niet bash, de bourne again shell, maar de oorspronkelijke POSIX compliant bourne shell) zit niet in ports maar is onderdeel van het base system in FreeBSD. Dit geld overigens voor alle Unixen, al is het in Linux meestal een linkje naar bash.
Volgens mij begreep je mij niet helemaal goed (zal wel aan mijn tekst liggen):

Wat ik wilde zeggen was dat alle programma's die je via het FreeBSD ports systeem installeert en een rc.d start script hebben altijd /bin/sh gebruiken en nooit bash.

Maar gezien de aard van de exploit doet dat er niet toe.
FreeBSD gebruikt standaard tcsh. Da's ook geen bash, maar zeker geen bourne shell :-)
Voor mensen die ermee werken in Git Bash (for Windows) zit het probleem ook.
Hmmm, dat is een vervelende bug. :(
Zelfs op mijn NAS werkt de test ook :(

[~] # env x='() { :;}; echo vulnerable' bash -c "echo this is a test"
vulnerable
this is a test
[~] #
Vreemde constructie, met die accolades. Ik gebruik die enkele aanhalingstekens waar dat hier allemaal tussen zit eigenlijk alleen maar voor enkele characters of escape codes alhoewel ik regelmatig scripts zie waarin ze dat wel doen. In csh (FreeBSD) werkt het ook.
Als ik die echo vulnerable vervang met sleep 3 dan krijg ik alleen "vulnerable' te zien gevolgd door een segfault crash.
Maar volgens mij heb je om een environment variabele te setten sowieso een user login nodig en heeft de uitgevoerde code ook de permissies van die user. Dat scheelt nogal, maar zonder meer een kwetsbaarheid.
Overigens snap ik dat met dat CGI-script niet helemaal. Webservers voeren toch over het algemeen alleen CGI-scripts uit die in de lokale server-scripts-directory staan? Hoe doe je zoiets remote zonder de server binnen te dringen en daar eerst een een shell CGI-script te plaatsen met die injectiecode?

[Reactie gewijzigd door blorf op 26 juli 2024 08:22]

Ik heb net wat zitten testen en als ik de 'echo vulnerable' vervang door 'ssh user@remote-host' dan wordt er een ssh sessie gestart naar de remote-host.

Dus heb ik het artikel nog eens doorgelezen en valt dit voorbeeld onder 'als je een reguliere shell hebt dan verandert er niets aan het gedrag'. Immers als je al een shell hebt kun je zo'n ssh commando net zo goed op de commandline zelf intikken.

Ik begrijp dat er bij cgi-scripts en dergelijke een kritiek lek is indien je er in slaagt om een variabele aan te vullen met commando's. Zelf ben ik er nog niet uit hoe ik dat voor elkaar zou moeten krijgen.

Waar ik vooral in ben geinteresseerd is de vraag of je zo uit een jail/restricted shell kunt komen...

[Reactie gewijzigd door dev0 op 26 juli 2024 08:22]

cgi script kan weer door middel van een andere kwetsbaarheid in een site geupload worden of diegene heeft al upload toegang tot de server en kan daarmee een kwetsbaar cgi script uploaden. Er zijn talloze manieren om iets op een server te krijgen ;).
Maar een cgi draait toch sowieso al in een shell? En kan toch sowieso al code op het systeem uitvoeren? Ik zie ook niet helemaal wat je nou extra kunt met deze bug...
Deels waar maar dingen zoals wireless routers enzo gaan naar de shell om te pingen of tracerouten en in dat soort gevallen is het dus best exploitable.

Daarnaast zet CGI automatisch HTTP headers om naar env variables. Als je een crappy webserver ofzo hebt dan kun je gewoon custom headers meegeven en worden die ook omgezet en heb je dus helemaal geen toegang tot de bash nodig ;).

[Reactie gewijzigd door Rutix op 26 juli 2024 08:22]

Ah nu vat ik m. Het is net zoiets als sql-injectie. Variabelen die een gebruiker van bv een cgi (die nooit geschreven is met kwaadaardige bedoelingen) zo aan kan passen dat de shell commando's voor een aanvaller uitvoert.
Het idee is dat zodra de volgende shell dan wordt opgestart (door iemand met meer permissies) ie ook dat scriptje uitvoert, en daar meer mee kan bereiken.
Ik zie nergens iets over meer permissies. Ik zie alleen iets over het uitvoeren van code door het zetten van een variabele. Die code zal nog steeds in dezelfde shell onder jouw user account draaien.
Wat betreft CGI:
So far, HTTP requests to CGI scripts have been identified as the major
attack vector.

A typical HTTP request looks like this:

GET /path?query-param-name=query-param-value HTTP/1.1
Host: www.example.com
Custom: custom-header-value

The CGI specification maps all parts to environment variables. With
Apache httpd, the magic string “() {” can appear in these places:

* Host (“www.example.com”, as REMOTE_HOST)
* Header value (“custom-header-value”, as HTTP_CUSTOM in this example)
* Server protocol (“HTTP/1.1”, as SERVER_PROTOCOL)
Bron: http://seclists.org/oss-sec/2014/q3/650
Vreemde constructie, met die accolades.
Op oss-sec staat het wel een beetje uitgelegd.
Bash supports exporting not just shell variables, but also shell functions to other bash instances, via the process environment to (indirect) child processes. Current bash versions use an environment variable named by the function name, and a function definition
starting with “() {” in the variable value to propagate function definitions through the environment. The vulnerability occurs because bash does not stop after processing the function definition; it continues to parse and execute shell commands following the function
definition. For example, an environment variable setting of

VAR=() { ignored; }; /bin/id

will execute /bin/id when the environment is imported into the bash process.
Je kan een shell functie definiëren voor een child proces. Dat kan met export -f of inderdaad met bovenstaande syntax. De accolades zijn dus de body van de functie. De dubbele punt hier heeft de functie van true, das een ouwtje. En het probleem zit 'm er natuurlijk in dat /bin/id wordt uitgevoerd op het importeren van deze knakker, wat wordt gedaan door bash -c 'iets uit te voeren'.
Net ook een testje gedraaid op mijn FreeBSD server:
$ su -
Password:
root@dave:~ # touch /tmp/deleteProof
root@dave:~ # ls -la /tmp/deleteProof
-rw-r--r-- 1 root wheel 0 Sep 25 08:58 /tmp/deleteProof
root@dave:~ # logout
$ env x='() { :;}; rm -f /tmp/deleteProof' bash -c "ls -la /tmp/deleteProof"
bash: rm: No such file or directory
Segmentation fault (core dumped)

Oeps, even het volledige path naar rm toegevoegd:
$ env x='() { :;}; /bin/rm -f /tmp/deleteProof' bash -c "ls -la /tmp/deleteProof"
rm: /tmp/deleteProof: Operation not permitted
Segmentation fault (core dumped)

Nog steeds een segfault, en de gestarte shell draait in elk geval niet met root privileges.
Misschien vanavond nog maar verder inlezen in wat er nou precies zo gevaarlijk is.
Vreemde constructie, met die accolades. Ik gebruik die enkele aanhalingstekens waar dat hier allemaal tussen zit eigenlijk alleen maar voor enkele characters of escape codes alhoewel ik regelmatig scripts zie waarin ze dat wel doen.
Enkele of dubbele aanhalingstekens maken niet uit. Die accolades zijn om een functie aan te geven. De inhoud van de functie maakt niet uit; 't gaat 'm om de extra commando's na de functie. Die definitie wordt uitgevoerd (in die shell is 'x' beschikbaar als functie, hoewel die niets doet in dit geval) en de extra commando's dus ook.
Maar volgens mij heb je om een environment variabele te setten sowieso een user login nodig en heeft de uitgevoerde code ook de permissies van die user. Dat scheelt nogal, maar zonder meer een kwetsbaarheid.
Een login is zeker niet nodig. Programma's die in de achtegrond draaien als daemon user van 't een of 't andere soort kunnen net zo goed environment variables zetten.
Overigens snap ik dat met dat CGI-script niet helemaal. Webservers voeren toch over het algemeen alleen CGI-scripts uit die in de lokale server-scripts-directory staan? Hoe doe je zoiets remote zonder de server binnen te dringen en daar eerst een een shell CGI-script te plaatsen met die injectiecode?
Die 'injectiecode' is alleen een demonstratie van het probleem. Het kan op meerdere manieren uitgevoerd worden. Bijvoorbeeld in je shell:

bash-3.2$ export x="() { echo hallo;}; echo vulnerable"
bash-3.2$ bash
vulnerable
bash-3.2$ x
hallo

(zie ook dat 'x' als commando beschikbaar is).

Zolang er dus een environment variable gezet is met die inhoud erin, kun je die code uit laten voeren. Apache zet er een aantal voor je als je een CGI uitvoert, waar je als client dus data in kunt proppen (middels verschillende headers en andere onderdelen van je request.)

De volgorde is dan: request naar cgi -> apache zet env variables -> apache start shell -> shell leest env variables en voert code uit -> bob is je oom.

[Reactie gewijzigd door CyBeR op 26 juli 2024 08:22]

:? Hoe weet je NAS dat dit voor hem bedoelt is? Of reageren alle (Linux/BSD) netwerkapparatuur op dit commando?
(Zou ook graag mijn NAS willen testen )
Je kan het ook op de shell van je NAS uitvoeren ?
ik heb een ssh sessie naar mijn NAS (QNAP TS-439PROII+) geopend en vervolgens de voorbeeld code uitgevoerd. En aangezien de meeste NASjes wat daemons draaien zoals een webinterface is deze kwtsbaarheid ook voor NAS eigenaren interessant.
Alleen het pachten van bash betekent wachten op de leverancier :(
Dank jullie voor de uitleg.
Ik kan niet in de SSH van mijn NAS (Schijnt wel te kunnenvia een crack maar heb het noot geprobeert bij gebrek aan Linux ervaring ), dus neem aan dat die van mij ook wel kwetsbaar zal zijn.
Wordt niet meer door leverancier ondersteund. Gelukkig staat hij niet open naar internet alleen zijn tijd en foutmeldingen geeft hij door
De laatste firmware release van QNAP fixt de bash kwetsbaarheid.
Op naar de volgende kwetsbaarheid (SSL v3) *zucht*
Nog een geluk dat Debian en Ubuntu al jaren default dash als systeem shell gebruiken.
Ik ga er vanuit dat je niet eerst even getest hebt of die shell vatbaar is voordat je deze comment plaatste? In mijn testrondje bleek namelijk dat óók dash en zsh evengoed vatbaar zijn (Het zijn en blijven bash-klonen natuurlijk, en blijkbaar is het vatbare stuk code gewoon meegeforked bij beide). 'sh' gebruiken helpt ook al weinig, aangezien die bij de meeste distributies naar bash danwel dash gesymlinkt is.

Edit: Ik interpreteerde de test zelf verkeerd. De eerder ingestelde env variabele wordt door de daarna gestarte bash uitgevoerd, niet door de shell waarin hij gedefinieerd wordt; Dash en zsh zélf zijn dus niet vatbaar, maar zolang bash wel geïnstalleerd is op het systeem en gestart kan worden dan is het systeem vatbaar, ongeacht in welke shell je op dat moment zit.

[Reactie gewijzigd door Remz-Jay op 26 juli 2024 08:22]

Dat ligt er maar aan of de programmeur van de aanroepbare scripts (cgi bin bijv) expliciet #/bin/bash als hashbang gebruikt of gewoon de standaard #/bin/sh gebruikt. Veel zullen idd bash gebruiken omdat ze specifieke bash features gebruiken, maar voor simpele taken gebruikt men vaak gewoon sh.
Als het een fork is, dan heb je ook de kans dat het lek erin zit ;)
De meegeleverde bash shell was overigens wel gewoon vatbaar. Dus alle scripts die #!/bin/bash beginnen hadden het probleem.

Voor Debian 'squeeze' moet je trouwens op 'squeeze-lts' zitten om de patch binnen te krijgen.
Op debian is dash standaard en verwijst /bin/sh dus niet naar bash. Er zijn niet veel scripts die expliciet bash gebruiken, maar een kan genoeg zijn.
grep /bin/sh * | wc -l
293
grep /bin/bash * | wc -l
19
Als je niet van al aanwezig (admin)scripts afhankelijk wilt zijn voor een exploit heb je al shell access nodig, en dan ben je al erg binnen.
Dhcp onder linux heeft toch gewoon zijn eigen native client, dat draait toch niet in bash?
En welke website gebruikt bash als backend, lijkt me ook niet de bedoeling?

De P-2812HNU-F1 van Telfort o.a. is in ieder geval niet kwetsbaar:
Failed to ping: env x='() { :;}; echo vulnerable' bash -c "echo this is a test"
Zal ook wel geen bash hebben misschien.

[Reactie gewijzigd door Soldaatje op 26 juli 2024 08:22]

Dhcp onder linux heeft toch gewoon zijn eigen native client, dat draait toch niet in bash?
dhclient wordt volgens mij afgevuurd via een bash script, en feed daar ook dingen aan terug die het script dan weer uitvoert, om bijvoorbeeld het IP adres in te (laten) stellen.

daar is dus een escape uit, met deze truuk. Moet je wel een dhcp server compromiteren natuurlijk, zodat ie bash escape code gaat terugspugen.
En welke website gebruikt bash als backend, lijkt me ook niet de bedoeling?
wie bepaald 'wat de bedoeling' is? De persoon die een website schrijft. Als diegene dat in bash wil doen, moet dat gewoon doen. Is geen enkel probleem. ik zou het het zelf ook niet doen, maar ik ken iemand die het wel gedaan heeft.

[Reactie gewijzigd door arjankoole op 26 juli 2024 08:22]

Ja, maar dingen die niet de bedoeling zijn doen kan bijvoorbeeld ook betekenen dat iemand een root shell aan het web hangt, dat houdt dan ook niet meteen in dat het de schuld van het systeem is maar er gewoon slecht gebouwd werd ;) Om dat het kan is het niet meteen 'goed' of de schuld van datgene wat misbruikt is he.
De client is native, maar gebruikt op de achtergrond Bash voor systeem configuratie
Maar het dhcp protocol moet het dus toestaan dat het bash commando's mag versturen/ontvangen?
Het moet eerst door de native dhcp-client heen voordat het bij bash kan komen lijkt me.
Dan lijkt me dat ook een bug van de native client die zo'n regel simpelweg doorgeeft aan bash?
Nee je kunt gewoon Bash code stoppen in velden die anders bijvoorbeeld de hostname of DNS suffix zouden bevatten
Precies, dus er vind geen controle plaats dan op die velden blijkbaar, dat is niet echt veilig en handig van de native client die het doorgeeft aan bash.

Op dit item kan niet meer gereageerd worden.