Por que a capacidade de definir funções em uma variável de ambiente não é um risco de segurança em si?

8

Pelo que entendi, geralmente é considerado seguro deixar alguém fornecer informações que serão armazenadas em uma variável ambiental. A vulnerabilidade do shellshock é um problema aqui porque significa que o código no final de uma definição de função dentro de uma variável de ambiente será executado quando uma nova instância do bash for lançada e você obviamente não quiser que alguém execute qualquer código que deseje em seu servidor . As próprias definições de funções aparentemente não são um risco de segurança e são permitidas porque elas precisam ser chamadas explicitamente para que seu código seja executado.

Minha pergunta é por que um usuário mal-intencionado não pode simplesmente definir uma função, contendo seu código malicioso como um comando comum como ls , e esperar que o script (ou o que estiver sendo executado) use esse comando em algum momento ?

Um exemplo do que tenho em mente:

$ export ls='() { echo "doing bad things..."; }'
$ bash -c ls
doing bad things...
    
por Reed Espinosa 26.09.2014 / 18:16

2 respostas

10

É um risco de segurança. Geralmente é por isso que você não pode fazer isso quando muda para outro contexto (controle remoto de um sistema, troca de usuários, etc).

Se você tiver a capacidade de criar qualquer variável de ambiente desejada, há várias maneiras possíveis de executar código arbitrário.
Tome $LD_PRELOAD como um exemplo. Se você tiver a capacidade de definir essa variável, poderá substituir as funções da biblioteca e inserir seu código lá. Você pode definir a variável $DISPLAY e redirecionar a exibição X na qual o programa se conecta para que você obtenha o controle do aplicativo.

É por isso que coisas como sudo eliminam o ambiente de todas as variáveis. sudo permite apenas algumas variáveis selecionadas. E dessas variáveis, ele as higieniza (passa pela variável $TERM , mas não se ela contiver caracteres incomuns).

    
por 26.09.2014 / 18:27
3

Eu diria que é, quando bash é seu / bin / sh. Não é uma característica do shell bourne, e eu aposto que não é uma característica do shell posix, na verdade eles podem querer proibi-lo expressamente.

O Bash é realmente mais derivado do korn, do que um shell do bourne, apesar de seu nome, e é o único shell tipo Korn que tem o recurso, e na minha opinião é o recurso do kitchensink que não tem virtudes práticas. Desenvolvedores que evitam recursos bash para padrões, como o shell bourne, o shell posix ou o subconjunto ksh88 que os shells modernos têm em comum, ou em outras palavras, se comprometem com boas práticas e idiomas padrão, ficam chocados quando o software está ligado linux e mac e agora potencialmente vulneráveis, já que os autores da exploração são livres para usar os 'bashisms', apesar de seus intentos. Até agora compatibilidade melhorada, quando invocada como / bin / sh, sobre outras derivações do shell korn, é somente se / bin / sh é seu shell de login, ou shell interativo, quando o bash se comporta mais como um shell bourne do que um shell korn, mas quando usado em scripts, você está livre para fazer qualquer coisa que o bash possa fazer, e ele nunca reclama ou avisa que você está usando recursos que realmente usam recursos do shell, ou exclusivos do bash.

Vou tentar convencê-lo de que é o recurso da pia da cozinha, com dois casos: você é um desenvolvedor incorporado, que cria dispositivos como roteadores, armazenamento conectado à rede  1 maior env, significa mais memória, mais custo, menos lucros então, se esse fosse um motivo para considerar o uso desse recurso do bash, você não deveria usar FPATH e autoload, recursos do ksh88 em vez disso? em vez de passar todo o byte de função para byte no ambiente? Você poderia até mesmo considerar a análise e a poda do ambiente por atacado, antes que ela chegue a um "shellscript" que poderia fazer uma comparação incorreta de uma variável, como apenas filtrar ^ $ (. *) $ E assim por diante ...

Isso ressalta o que é único sobre isso, não importa qual seja a variável, e o script não precisa fazer referência ou usar a variável, ela ainda pode estar vulnerável.

#!/bin/sh
exec /usr/local/myapp/support/someperlscript.pl

Para tudo o mais sob o sol, o acima deve ser tão seguro quanto o script em perl, você não está usando as variáveis, como você poderia fazer um erro? Mudando para

#!/bin/bash -norc
exec /usr/local/myapp/support/someperlscript.pl

Também não ajuda, isso não tem nada a ver com ENV ou algo parecido - todo mundo fica queimado porque o bash precisa ser único. O fato de que bash versão 2 tem o problema, para mim prova que ninguém nunca usa esse recurso para seus aplicativos, porque caso contrário deve não ter se esgueirado por esse tempo. E o que é pior, basicamente não há como evitar esse recurso . Aqui está um exemplo com: com 'su -', que se você perguntar a alguém, a explicação é que ele descartará o ambiente, verifique a man page e você encontrará apenas 99.9%. Eu testei dessa maneira, já que neste sistema / bin / sh é o shell de login do root, e / bin / sh é bash MAS , neste exemplo eu tento endurecer meu .bash_profile. Renomeiei meu existente para root (que está habilitado), mas meu pensamento era su, depois possivelmente sudo, enfim, mudei para isso:

exec env -i TERM=vt102 LOGNAME=root USER=root HOME=/var/root /bin/ksh -i

Então, estou lançando o ambiente completamente e uso um env mínimo e, em seguida, executando um shell que não deveria ter o problema, no lugar do processo atual. Em seguida, no lugar do exemplo padrão, tente:

%dock='() { echo -e "\e[2t\c"; echo dockshock;} ; dock' su 

Isso ilustra como isso não tem nada a ver com a análise de qualquer função específica, e uma exploração pode se referir e usar a função. Você pode imaginar a função com lógica para testar se raiz, etc. Neste caso, é apenas uma forma modificada de uma função para iconificar ou encaixar uma janela de terminal, usando uma seqüência de escape, que é bastante padrão, então depois eu clicando para deiconify, vejo dockshock - mas, e daí? Agora tente isto:

%TERM='() { echo -e "\e[2t\c"; echo dockshock;} ; TERM' su - 

E adivinha o que? A janela é sugada para o banco dos réus. Aqui está o que parece depois ..

%TERM='() { echo -e "\e[2t\c"; echo dockshock;} ; TERM' su -
Password:
dockshock
# env
_=/usr/bin/env
HOME=/var/root
LOGNAME=root
TERM=vt102
USER=root
# echo $0
/bin/ksh
#

Então, muito, muito para isso! As funções exportadas na verdade têm prioridade sobre os scripts rc. Você não pode evitá-lo.

    
por 27.09.2014 / 13:44