Checklist de Segurança para Aplicações PHP
por
em 17-12-2012 às 11:19 (6676 Visualizações)
Este é um pequeno checklist de algumas medidas que podem ser colocadas em prática para deixar sua aplicação PHP mais segura. Não é necessário ser um expert na área para conseguir um nível de segurança suficiente para bloquear a maioria dos ataques.
Básico:
- Senhas fortes devem ser utilizadas (maiúsculas, minúsculas, números e símbolos);
- As senhas devem ser armazenadas de forma segura (não guardar as senhas em texto puro);
Código PHP:
register_globals = Off;
display_errors = Off;
disabled_functions = dl,exec,system,passthru,shell_exec,proc_open,popen,show_source;
allow_url_fopen = Off;
allow_url_include = Off;
open_basedir = "apenas o path de sua aplicação";
Entrada de Dados:
- Todos os valores vindos de $_GET, $_POST, $_COOKIE, $_REQUEST são considerados contaminados por padrão.
- Todo dado de entrada deve ser validado;
- Caracteres \0 (NULL) devem ser descartados;
- Verificar o comprimento dos dados;
- Caracteres unicode devem ser descartados onde for possível;
- Utilizar funções como add_slashes e mysql_real_escape_string;
- Arquivos não devem ser abertos utilizando dados vindos do usuário. Ex:
Código PHP:
$file = $_GET['file']; include("$file".php);
Upload de Arquivos:
- Verificar o tipo do arquivo, não confiar apenas em sua extensão;
Código PHP:
mime_content_type($file);
- Checar o tamanho do arquivo;
- Verificar o conteúdo do arquivo, use scanners de malware se necessário;
- Arquivos enviados não devem ser movidos para um lugar acessível diretamente via browser;
- Arquivos enviados não devem ser carregados via in include();
Banco de dados:
- Qualquer comunicação com o banco de dados de ser parametrizada/escapada - Leia;
Código PHP:
mysql_real_escape_string();
- A aplicação não deve ter mais acesso do que o necessário ao banco de dados, por exemplo ter acesso de escrita se somente opera funções de leitura;
- Acesso remoto ao banco de dados deve ser desabilitado se possível;
- Preparar as querys com PDO;
Autenticação:
- Bloquear endereço IP / conta no caso de falhas de autenticação seguidas (Evitar ataque de brute force);
- Utilizar recursos como CAPTCHA;
- Utilize SSL para evitar MITM;
- Não salvar a senha em cookies;
- Utilizar salts diferentes para cada usuário;
- Não utilizar MD5 para gerar/armazenar a senha;
- As páginas de recuperação de senha não devem mostrar os emails existentes;
- As páginas que enviam email devem ter algum tipo de limitação de envio;
Sessões:
- A sessão deve ser destruída no logout;
Código PHP:
session_destroy();
- A sessão deve ser recriada toda vez que alguma operação importante for executada (evitar session hijack);
Código PHP:
session_regenerate_id();
- Armazenar as sessões em locais diferentes para cada site rodando no servidor;
- Não aceitar IDs de sessão gerados externamente para evitar Session Fixation (Definir timeout na sessão);
- Expirar sessões antigas;
- Não utilizar o mesmo diretório para armazenar sessões e arquivos enviados;
Parceiros/Acessos Externos:
- Referências externas devem utilizar tokens/chaves para evitar CSRF;
- Não confiar no REFERER;
- Verificar se imagens,páginas que demorem para carregar, CSS,etc não forneçam informações confidenciais se carregadas remotamente ;
Variados:
- Utilize suhosin;
- Utilize a função htmlentities() para qualquer conteúdo que o usuário irá visualizar, para evitar XSS;
Código PHP:
echo htmlentities($str);
- Mensagens de erro devem ser tratadas; Não exiba a mensagem de erro padrão do banco de dados, isto é uma fonte de informação importante para SQLInjection. Claro que Blind SQLInjection ainda poderá ocorrer se os dados não forem tratados corretamente mas pelo menos dificulta;
E um dos MAIS IMPORTANTES:
"Security through obscurity" ou "Segurança através de obscuridade"
NÃO É SEGURANÇAPara quem não conhece esta "técnica", se é que podemos chamar isto de técnica, é o uso de artimanhas para tentar esconder informações fazendo com que elas fiquem mais difíceis de se ler a olho nú.
Por exemplo:
- Colocar todo código em apenas uma linha;
- Trocar o texto através de funções, ex:
Isto se traduz em:Código PHP:
$e = str_replace('y','e','yxyc');$e(ls);
Código PHP:
exec(ls);
- Utilzar funções para codificar o texto, ex:
Isto se traduz em:Código PHP:
eval(ZXhlYyhscyk7);
Código PHP:
exec(ls);
CONCLUSÃO
A grande regra de ouro é nunca revelar mais informações do que o necessário. Com este checklist você no mínimo, ficará muito mais protegido contra ataques XSS, SQLi, CSRF, Brute Force, Session Hijack e Session Brute Force;
Apesar de ser um checklist com funções para PHP, boa parte pode ser aplicado a outras linguagens.
Desenvolvido por: Rafael M. Capovilla AKA 'iceman' e Camilla Lemke
Para dar sugestões para o próximo artigo, basta comentar aqui!
Comentários
+ Enviar Comentário