Escolar Documentos
Profissional Documentos
Cultura Documentos
| __ (_) | | | | | | | |
| |__) | _ __ | | _| |__| | __ _| |_
| ___/ | '_ \| |/ / __ |/ _` | __|
| | | | | | | <| | | | (_| | |_
|_| |_|_| |_|_|\_\_| |_|\__,_|\__|
PinkHat (Un)Security Team 2009
##########################
Índice - MySQL Injection
##########################
SQL Injection
[0x00] - Sobre o ataque
[0x01] - Onde acontece
[0x10] - Verificando a vulnerabilidade
[0x11] - Atacando!
[0x12] - Capturando dados
[0x13] - MySQL Dump
[0x14] - Burlando filtros
Blind Injection
[0x00] - Sobre o ataque
[0x10] - Verificando a vulnerabilidade
[0x12] - Achando uma tabela
[0x13] - Achando uma coluna
[0x14] - Capturando dados
#########################
[0x00] - Sobre o ataque
#########################
Antes de começar o tutorial, eu recomendo que você tenha uma noção sobre SQL,
nem que seja
uma noção mínima para não ter dificuldade em entender o funcionamento de um ataque
em um site
vulnerável a (Blind) MySQL Injection
O único requerimento para este ataque é um browser comum. Inicialmente voc?s
não precisarão
de scanners ou tools para explorar a falha, portanto, procure ENTENDER o que está
escrito aqui
pois creio que atualmente, esta é a falha mais encontrada na internet, porém não é
a mais fácil
de explorar e fazer o deface em um web site. Vocês não terão uma phpshell em mãos
onde só irão
clicar no botãozinho e a phpshell altera "automaticamente" a index de um site, como
acontece em
falhas de include (Local File Inclusion e Remote File Inclusion).
########################
[0x01] - Onde acontece
########################
Como alguns de vocês devem saber, este tipo de ataque não depende da
linguagem de programação
do script (a correção da falha depende), e sim do banco de dados SQL, ou seja, você
pode encontrar
a vulnerabilidade em um site feito em PHP, mas também pode encontrar em um site
feito em ASP.
No caso desta matéria, irei abordar os ataques em um servidor MySQL e PHP. A
falha também não
depende do tipo da requisição, ou seja, é possível encontrar vuln em requests GET,
POST, e o que
seja manipulável pelo cliente. Nesta matéria eu irei exemplificar com requisições
GET, já que é
a mais manipulável e a melhor para usar nas explicações. Eu usarei um sistema de
notícias que
pega o ID da notícia via GET durante toda a matéria.
-------------------------------
SQL INJECTION ATTACK
-------------------------------
########################################
[0x10] - Verificando a vulnerabilidade
########################################
SQL Injection só é possível quando o site te informa qual o erro que o banco
de dados caso
não seja possível fazer a consulta no banco de dados. Por exemplo:
<?php
$id = $_GET['id'];
$q = "SELECT * FROM noticias WHERE id = '$id'";
$r = mysql_query($q) or die(mysql_error());
?>
Como vimos ali, caso não seja possível enviar a consulta ao MySQL, o script é
interrompido exibindo a mensagem de erro da operação enviada ao MySQL. Se eu entrar
em
http://www.fvox.com/noticias.php?id=10%27 (lembrando que %27 equivale a uma aspa
simples ').
A query a ser enviada seria a seguinte:
SELECT * FROM noticias WHERE id = '10''
É claro que o servidor pode emitir outros erros, mas desde que exiba um erro,
já é
alguma coisa para que você possa realizar seus penetration tests com grande
esperança,
o que te motiva bastante.
####################
[0x11] - Atacando!
####################
SELECT * FROM noticias WHERE id = '$id' order by 1/* Ignora o resto da query
###########################
[0x12] - Capturando dados
###########################
Agora iremos utilizar o operador UNION, que também não irei explicar para que
serve...
Essa porra tá com 110 linhas e eu ainda nem cheguei na metade, puta que pariu.
Quando você injetar isso na URL, o site irá imprimir um "número" na tela,
seja ele 1, 2
ou 3. Se o site mostrou um 2 na tela, substituia o número 2 por "@@version". O site
irá
imprimir a versão do banco de dados na tela.
Se colocarmos database() no lugar do 2, o site irá imprimir o nome do banco
de dados
em que a tabela está.
Agora vem uma parte chata. Você terá que chutar o nome da tabela! Isso mesmo,
você
terá que adivinhar o nome da droga da tabela. Você pode tentar admin, users,
usuarios,
membros, cadastros, administrador, etc.
Caso a versão do MySQL seja 5.xxxx, você pode recorrer a uma técnica chamada
MySQL Dump, onde você consegue o nome das tabelas e colunas por meio da tabela
information_schema. Se a versão do MySQL for 4 e você não conseguir adivinhar
o nome da tabela, desista do site. Como eu usei a versão 5.1.30-gpl-log como
exemplo
desta matéria, eu irei abordar como "dumpar" as tabelas e colunas mais para frente.
Deste modo, chegamos a conclusão de que há uma tabela chamada admin, que
certamente
guarda dados do administrador e que este tutorial está ficando muito grande pro meu
gosto.
Agora que descobrimos a tabela, iremos novamente nos foder para descobrir o
nome das colunas
para pegar as informações do admin.
#####################
[0x13] - MySQL Dump
#####################
---------------------------------
BLIND SQL INJECTION ATTACK
---------------------------------
#########################
[0x00] - Sobre o ataque
#########################
Como eu já expliquei acima, SQL Injection é uma técnica baseada nos erros que
o script
que realiza a conexão nos mostra em caso de erro. A principal diferença entre o SQL
Injection normal e o Blind SQL Injection é que em Blind, não necessitamos das
informações
que o servidor nos mostra.
É por isso que o nome do ataque é "Blind Injection" (Injeção cega em
português). Nós apenas
injetamos algo e o servidor retorna apenas valores booleanos (true ou false)
durante o ataque.
########################################
[0x10] - Verificando a vulnerabilidade
########################################
<?php
/* [...] */
$id = $_GET['id'];
$sql = "SELECT * FROM noticias WHERE id = '$id'";
$q = mysql_query($sql);
$r = @mysql_fetch_row($q);
/* [...] */
?>
####################
[0x12] - Achando uma tabela
####################
#############################
[0x13] - Achando uma coluna
#############################
###########################
[0x14] - Capturando dados
###########################
Para pegar o conteúdo de uma coluna, nós temos que adivinhar outra coisa, mas
dessa vez é algo mais simples. Temos que adivinhar a quantidade de caracteres que
o valor dessa coluna possui.
Por exemplo, se a senha do admin que está na coluna PASSWORD da tabela ADMIN
é
"synyster", vimos que esta senha possui 8 caracteres. Agora vamos montar o exploit:
Neste caso, o site iria retornar false, pois como citei no exemplo acima, a
senha
do admin é "synyster". Se eu tivesse colocado o valor da letra "s" ali, o site iria
retornar true. Agora, para exemplificar melhor, eu irei pegar o segundo caractere:
O site retornou TRUE, pois o segundo caractere é 121 (y). Realmente é bem
chato ficar
testando caractere por caractere, mas há diversas tools por ai que facilitam este
trabalho.
Fim do tutorial.
Atenciosamente,
fvox.