Bem vindo ao SOS Designers

Faça o seu cadastro gratuito no Portal SOS Designers e tenha um acesso personalizado.

Empresas

Cadastre gratuitamente suas vagas, crie sua propria Lista de Curriculos Favoritos, e tenha um acesso personalizado.

Usuarios

Cadastre gratuitamente seu curriculo, crie sua propria Lista de Noticias Favoritas e tenha um acesso personalizado.

Área de Empresas | Vagas

Área de acesso a empresas cadastradas que desejam postar vagas de empregos no Portal e pesquisar curriculos.

Cadastre-se gratuitamente
Esqueceu a sua senha?

Área de Usuarios | Curriculos

Área do Usuario que deseja cadastrar seu curriculo e pesquisar vagas.



Cadastre-se gratuitamente
Esqueceu a sua senha?

4 Visitantes Online
Redes Sociais
Siga o Portal SOS Designers no Twitter Siga o Portal SOS Designers no Facebook

PHP


Você está aqui: Home » PHP » Segurança em programação PHP

Segurança em programação PHP


Pesquisar no Portal SOS Designers





Tempo Real



Participe da Comunidade SOS Designers

Siga o SOS Designers








SOS Designers
Segurança em programação PHP

Por: Sulamita Garcia

Este artigo irá fornecer a você uma visão geral de várias caracteristicas de segurança com PHP e oferecer conselhos para práticas de programação segura em PHP.

PHP tem alcançado uma presença sólida e estável na Web nos últimos anos, e sua popularidade como uma linguagem de scripts para servidores está crescendo. Seu uso primário é para prover interfaces geradas dinâmicamente entre usuários e o servidor. Como tal, scripts PHP são uma presa natural de ataques. Apesar do fato de a linguagem ser projetada com segurança em mente, a familiaridade com seus mais perigosos aspectos e adaptação a direção comum de programação segura é essencial para minimizar a possibilidade de comprometer a segurança. O objetivo deste documento é oferecer uma visão geral de várias caracteristicas de segurança com PHP e oferecer conselhos para práticas de programação segura em PHP.

Introdução

PHP (PHP Hypertexto Preprocessor) é uma linguagem de script para servidor que facilita a criação de paginas Web dinâmicas embutindo códigos PHP em documentos HTML. Ele combina muitas das mais refinadas caracteristicas de Perl, C e Java, e adiciona seus próprios elementos à mistura para dar aos programadores Web grande flexibilidade e poder no projeto e implementação de páginas dinâmicas para Web. Porem, como qualquer ferramente poderosa, existem certos riscos e perigos associados com o uso de PHP. Este artigo objetiva alertar o leitor de tais detalhes sutis desta linguagem. Estando consciente dos riscos e observando algumas regras simples de programação segura, é possivel diminuir significativamente o risco de comprometer a segurança.

Nas sessões seguintes, nos iremos identificar um numero de causas que comumente levam a violações de segurança de scripts PHP e ultimamente os sistemas os quais estes scripts tem sido executados. Nos iremos então desenvolver algumas diretivas para fortalecer a segurança do PHP e para escrever codigos seguros. Desenvolvedores Web e administradores de sistema devem manter em mente, porem, que estas diretivas apenas identificam algumas praticas que podem reduzir o risco de comprometer a segurança. Não existe uma solução definida que possa resolver todos os problemas de segurança, de fato, o verdadeiro conceito de um sistema que está num estado completamente seguro é irreal. Ao inves disso, segurança deve ser vista como um processo evolutivo, requerendo constante supervisão. Este artigo provê uma base para entendimento de caracteristicas relacionadas ao PHP e dá uma visão geral mais ampla do topico.

Fontes de Furos de Segurança

PHP pode rodar tanto como uma aplicação CGI como um modulo integrado de um servidor Web. Sem levar em conta seu modo de execução, o interpretador PHP tem o potencial de acessar virtualmente toda parte do host - o sistema de arquivos, interfaces de rede, IPC, etc.

Consequentemente, ele tem o potencial para fazer (ou ser forçado a fazer) muito estrago. Para prevenir ataques, o programador deve estar prevenido de tudo que pode sair errado a qualquer hora durante a execução do programa. Esta é uma tarefa formidável. Programas se tornam muito complicados muito rápido. No entanto, conhecimento dos pontos de fraqueza de um sistema e os modos comuns de ataque podem ser um bom caminho para incrementar a segurança. Isto aplica-se ao PHP tanto quanto a qualquer outra parte do software. Então, nesta sessão iremos examinar vários fontes de vulnerabilidades potenciais em scrips PHP e iremos tirar algumas conclusões generalizadas. Nós usaremos esta informação em outra sessão para desenvolver um conjunto de diretivas para programação segura em PHP.

Entradas de usuário confiáveis

As mais comuns e mais serias vulnerabilidades em scripts PHP, e sem dúvida em qualquer aplicação Web, são devido a uma validação de entrada de usuário precária. Muitos scripts usam informações que o usuário forneceu num formulário Web e processam estas informações de várias maneiras. Se esta entrada de usuário é confiada cegamente, o usuário tem o potencial de forçar comportamento não desejado no script e no host.

Para tornar as coisas piores, PHP registra todo tipo de variáveis externas no espaço global. Variaveis de ambiente pro exemplo são simplesmente acessadas por seus nomes de qualquer lugar dentro do script. Então você pode apenas espiar em $HOSTNAME e $PATH para ter pedaços de infomação. Nomes de campos enviados de forms GET ou POST são tambem acessiveis da mesma maneira. Existem muitos problemas com isso.

Primeiro, não existe um modo de assegurar que variáveis externas contenham dados que podem realmente ser confiáveis. (A próxima sessão discute isso com otimos detalhes.)

Segundo, devido a habilidade do PHP para fazer tudo disponivel globalmetne, nenhuma variável pode ser confiável novamente, seja interna ou externa. De fato, imagine o seguinte cenário:

$tempfile = "12345.tmp";

...
# faço alguma coisa com $tempfile aqui
# e algum processamento de formulário ...

unlink ($tempfile);

Mesmo se você manteve $tempfile seguramente antes de liberar o link, a ultima instrução ainda é muito perigosa. Um atacante pode manipular o seu proprio form contendo um campo similiar a isto:

PHP irá inserir o campo nome no espaço global como $tempfile, este modo sobrescrevendo o valor original da variável. Depois, nós iremos considerar um modo de proteger contra este tipo de ataque configurando O PHP para não tornar variaveis externas globalmente acessíveis.

Variáveis em ambiente confiável

Quando vc digita "ls" no prompt do UNIX, o shell vai atraves de uma lista de diretorios procurando por um programa chamdo 'ls'. Tão logo quanto ele encontra isto em algum lugar, como no /bin, por exemplo, o shell executa o programa e espera pacientemente pela seu retorno. A lista de diretorios onde o shell irá procurar o programa é especificado em uma variável ambiente, usualmente $PATH. Similarmente, quando você usa o include() ou require() para um arquivo de um script PHP, o sistema irá procurar por ele numa lista específica de diretórios; a variável ambiente $LD_LIBRARY_PATH especifica o caminho para bibliotecas dinamicamente carregadas.

O script não tem controle sobre o conteudo de variáveis de ambiente no momento que inicia a execução. Um adversário pode modificar o caminho para apontar para uma versão tipo Trojan do programa que está sendo chamdado ou o arquivo que está sendo incluido. Este é um modo fácil para hackers terem codigos hostis rodando no sistema.

Alguns sites restringem o acesso ao conteudo baseado no link de onde o usuário vem. Eles usam a variável $HTTP_REFERER para determinar isto. Mas já que esta informação chega do browser, não há nada que pare o usuario de associar um valor arbitrário. Tais formas de autenticação não são nada confiáveis.

Mesmo que a informação não venha do usuário, variáveis de sistema ainda assim não são confiáveis. Na maioria dos sistemas Unix, as variáveis de ambiente são armazenadas no topo da pilha de sistema. Agora, PHP faz seu proprio gerenciamento dinâmico de memória, então não existe um risco real de buffer overflow em scripts PHP. Mas um hacker pode ainda explorar algumas partes do software que estão rodando no servidor para ganhar acesso à pilha de execução. Por causa do modo que a pilha é estruturada, ele pode agora sobrescrever o valor de variáveis de ambiente. Consequentemente, o script PHP que confia cegamente nestas variáveis não está nada seguro.

De uma perspectiva segura, variáveis de ambiente e dados de entradas de usuários não são realmente muito diferentes. Eles podem representar dados de origem desconhecida que podem ser hostis. Deste modo, seu uso deve ser minimizado sempre que possível, e seu conteudo examinado e filtrado o resto das vezes. Uma boa pratica é redefinir todas as variáveis de ambiente que irão ser usadas no script antes de realmente usa-las. Isto não é sempre possivel, mas é uma ajuda a oferecer um grau de confiança um pouco mais alto no seu conteúdo.

Chamando programas externos

A ilustração mais direta de dano inflingido por entradas de usuário inválidas é provavelmente a execução de programas com nomes de usuário especificados ou argumentos.

Evidentemente, uma chamada como system($dados_usuario) é insegura porque isto permite o usuário executar comandos arbitrários no host. Mais ainda, uma chamada do tipo exec("algumprog", $args_usuario) é tambem insegura porque o usuário pode fornecer caracteres que tem significado especial para o shell. Um ponto e virgula nos argumentos por exemplo irá significar o fim do primeiro comando e o começo do segundo. Já que php sempre passa tais strings para o shell, isto é sempre perigoso. Isto inclui chamadas system(), exec(), popen(), backticks, etc.

O seguinte é um exemplo real de uma chamada popen() insegura, partindo de uma aplicação Web atualmente distribuida livremente:

function Send($sendmail = "/usr/sbin/sendmail")
{
if ($this->form == "") {
$fp = popen ($sendmail."-i".$this->to, "w");
}
else {
$fp = popen ($sendmail."-i -f".
$this->from." ".$this->to, "w");
}
}

A variável $this->from vem diretamente de um campo do formulário, onde quem quer que seja que esteja enviando a mensagem digita ali seu endereço de email. Uma vez que esta entrada não é validade em nenhum lugar, o usuário pode enganar o script introduzindo todo tipo de coisas ruins com entradas similares a esta:

dummy@dummy.com badguy@evil_host.com Se eles forem mais criativos, eles pode provavelmente até mesmo fazer um worm completo ou um virus e injetar nesta entrada.

A solução é filtrar cuidadosamente toda entrada de usuário antes de passa-la para o shell. Mais tarde, nos iremos considerar alguns modos de fazer isto em PHP.

Interações com Bases de Dados

PHP faz interações com vários bancos de dados diferente, e faz isto facilmente a partir de scripts. Apenas interagindo com outros programas atraves do shell, entretanto, isto pode ser um problema de segurança. Muitas vezes scripts PHP usam entradas de um formulário Web para contruir strings para requisições (query) SQL.

mysql_db_query ($DB, "SELECT something
FROM table
WHERE name=$username");

Neste exemplo, o usuário pode usar um ponto-e-virgula na entrada para finalizar a requisição atual e fornecer comandos arbitrários para a base de dados. A entrada ";drop db database" irá expandir a requisição "SELECT algumacoisa FROM tabela WHERE name=; drop db database", o que irá resultar em um erro (porque a primeira parte da requisição é agora inválida) seguida de um drop bem sucedido da base inteira.

Os privilégios do script podem ser ajustados para limitar o dano que ele pode causar na base, mas isto não remedia completamente o problema, uma vez que o usuário pode ainda fazer requisições para extrair informações sensíveis. Se a entrada do usuário precisa ser fornecida para a base de dados, a entrada deve ser primeiro examinada e filtrada para evitar metacaracteres, como nos iremos mostrar depois.

Includes e Opens URL

PHP generaliza o conceito de um arquivo para incluir

include
("http://some.site.com/some_script.php");

Ele saberá como trazer o arquivo daquele local e inclui-lo no seu script. Voce pode tambem abrir arquivos remotos para leitura do mesmo modo. Isto pode ser potencialmente perigoso, uma vez que existe a possibilidade do site remoto estar comprometido ou a conexão de rede ser enganada. Neste caso, você está injetando codigo desconhecido e possivelmente hostil diretamente no seu script com um include() como este. Dependendo de o que você faz com o arquivo, um fopen() de um local remoto pode ser perigoso da mesma forma. É claro que contruições do tipo include($dado_usuario) são ainda outro problema, similar àqueles discutidos na sessão anterior.
Se não for absolutamente necessario, esta caracteristica de PHP é melhor desabilita-la. A diretiva de configuração allow_url_fopen controla este comportamento.

Vulnerabilidades no interpretador

O interpretador PHP tem tido vulnerabilidades de segurança nos diferentes estágios do seu desenvolvimento.

No PHP3 e algumas versões do PHP4 tem sido encontrados vulnerabilidade para formar strings de ataque nas funções de log, por exemplo. Estas versões de PHP empregam chamadas para as funções syslog() e vsnprintf() do C para fazer o seu log (quando está habilitado). O problema é que PHP passa a mensagem de log diretamente como a string para estas funções, e é muito possível que a mensagem de log contenha uma entrada de usuário. Um invasor pode usar isto para comprometer remotamente o PHP - habilitando servidores que ainda executem este codigo, a menos que estes servidores tenham desabilitado o log de erros PHP e warnings.

O modo como o PHP trata de arquivos carregados pelo usuário pode tambem ser problemático. A razão para isto é que PHP irá definir uma variável global que tem o mesmo nome que o arquivo submetido no formulário Web. PHP irá então criar este arquivo em um diretório temporário e armazenar o upload ali, mas ele não irá checar se o nome do arquivo é válido. Um invasor pode fazer seu proprio formulário especificando o nome de algum outro arquivo e o submetendo. PHP irá então executar o outro arquivo, o qual pode conter informações sensíveis. Deste modo, o script deve sempre checar explicitamente se a variável que contem o nome do arquivo carregado contem um caminho válido para um arquivo temporário. Versões mais novas do PHP (depois da 4.0.3RC1 e depois da 3.0.17RC1 para PHP3) oferecem a função is_uploaded_file($path) que faz esta checagem mais simples.

Hosts rodando PHP devem seguir advertencias de segurança relatadas para o produto e atualizar para a ultima versão recomendada do PHP imediatamente depois das correções de segurança serem liberadas.

Na Parte 2, eu irei encerar nossa observação da segurança do PHP com mais cuidado nas linhas da programação, filtrando entradas de usuário, e configuração.

--------------------------------------------------------------------------------
Sobre o autor Jordan Dimov é um consultor da Cigital Inc em Dulles, VA, e membro do grupo de segurança de software da Cigital.
Tradução e adaptação: Sulamita Garcia

Fonte: www.superphp.com.br


Deixe seu comentário:





© Copyright 2002-2013
Portal SOS Designers
Webmaster: Luiz Antonio Bovi