segunda-feira, 16 de julho de 2012

O que é SQL Injection artigo muito bom

O que é SQL Injection artigo muito bom



O que é SQL Injection

Sql Injection é conhecido pelo método utilizado para inserir, apagar, editar, entre várias outras funções SQL em ataques a banco de dados através de formulários do tipo texto e password, onde o atacante poderá inserir um usuário em sua tabela do banco de dados, dando-o permissão para acessar todo o sistema ou por exemplo, apagar todos os dados contidos nela .

Exemplos de Ataque

No exemplo abaixo, demonstraremos em ASP as possíveis falhas que podem ocorrer nos websites. Utilizaremos abaixo um exemplo, iremos construir uma tabela de usuário com as seguintes colunas :
- Login - varchar (255) 
- Senha - varchar (255) 
Após criada, executaremos a query :
SELECT * FROM usuarios WHERE login = '[login]' AND senha = '[senha]'; 
Nos scripts ASP, iremos concatenar esta query em uma variável para construir uma consulta dos dados do usuário usando a seguinte linha: 
var query = "SELECT * FROM usuarios WHERE login = '" + login +"' AND senha = '" + senha + "'" ;

Se o login for uma aspa simples (') a consulta que irá acontecer se torna:
SELECT * FROM usuarios WHERE login = ' ' ' AND password = '[password]' ;
Isto é uma sintaxe inválida de SQL e irá produzir uma mensagem de erro no browser do usuário:

Microsoft OLE DB Provider for ODBC Drivers error '80040e14'
[Microsoft][ODBC SQL Server Driver][SQL Server]
Unclosed quotation mark before the character string and senha=.

A aspa simples fornecida pelo usuário fechou a primeira aspa simples e a segunda aspa simples gerou o erro pois não estava fechada. O atacante pode agora começar a injetar uma string na query para manipular o seu comportamento, por exemplo para efetuar o logon como o primeiro usuário na tabela de usuários você poderia colocar no campo de login:
' or 1=1 --
Isto converte a busca para:
SELECT * FROM usuarios WHERE login = ' ' or 1=1- - ' AND senha = '[senha]';
Os dois hífens significam um comentário em Transact-SQL, então todo o restante da linha é ignorado. Como 1 é sempre igual a 1, esta query irá retornar a tabela de usuários inteira. O script ASP irá aceitar o logon pois resultados foram retornados e o cliente será autenticado como o primeiro usuário da tabela.
Se conhecer um usuário, pode logar com o seu nome:
' or login='admin' --

O SQL Injection não ocorre apenas se o usuário não escapear as aspas simples, outra ocorrência é:
sql = "delete from tb_videos where vd_id = " & request("id") 

Neste caso se o usuário inserir como entrada "0 or 1=1" a query acima irá apagar todos os vídeos do banco de dados.


Visto até aqui pode-se ter uma idéia do quão exposto está uma aplicação que não implementa segurança contra esta técnica de invasão.


Formas de Correção

Estas informações abaixo são apenas exemplos de formas para correção de possíveis ataques ao Banco de Dados, porém, existem outros métodos também válidos, mas que por fugirem do escopo do artigo, não serão abordados aqui.

Em ASP uma forma simples para correção deste problema é utilizar uma instrução replace nos caracteres chave, como no exemplo abaixo:
strSenha = Replace(strSenha, "'", "");

Basicamente ele substitui o (') por nada, isto é uma forma de corrigir o problema.


Em PHP existem algumas formas de resolver o problema, uma é usar a função: mysql_real_escape_string(); e outra é usar a função: stripslashes();.

Exemplificando a solução com o stripslashes, temos:

Para toda variável inteira fornecida pelo usuário, passe a seguinte função: $var = intval($var);
Isto elimina todos valores não numéricos, deixando apenas valores inteiros

Para as demais variáveis, antes de fazer qualquer operação no banco, passe a seguinte função:
$var = addslashes($var);

Esta função retorna uma string com barras invertidas antes de caracteres que precisam ser escapeados. Estes caracteres são aspas simples ('), aspas duplas ("), barra invertida (\) e NULL (o byte NULL).

A função stripslashes() retorna uma string com as barras invertidas retiradas. (' se torna ' e assim por diante.) Duas barras invertidas (\\) se tornam uma (\).

Por fim, inclua o arquivo ctracker.php no cabeçalho de todas as páginas que recebem variáveis como parâmetro. Exemplo:
<?php
      require_once("ctracker.php");
      // Aqui em baixo fica o conteúdo
?>


Obs: Lembre-se de alterar a 5ª linha do código, nela é setada qual a página será exibida quando o sistema identificar uma tentativa de invasão.

Em Perl, a solução da SQL Injection é apenas baseada nas aspas. Na maioria dos casos a substituição de uma aspas simples por aspas duplas resolve o problema. A instução em Perl para isto é:
$sql = sprintf 'SELECT name FROM usuarios WHERE nome%s AND senha=%s,
   $dbh->quote($Q::nome),$dbh->quote($Q::senha);

Todas as soluções aqui apresentadas são baseadas no mesmo processo de escapeamento de caracteres especiais, no caso Aspas.


Arqui filtro ant - sql




<?php
//****************** CONFIG ****************//
// pagina que será impessa quando a tentativa de invasao for detectada
$page = "http://[sua_pagina_de_invasao]";
//****************** CONFIG ****************//


// Cracker Tracker Protection System
// Created by: Christian Knerr - www.cback.de
// phpBB Users: Please use our complete phpBB2 Mod!
// Version: 2.0.0
//
// License: GPL
//
// Begin CrackerTracker  StandAlone
//
  $cracktrack = $_SERVER['QUERY_STRING'];
  $wormprotector = array('chr(', 'chr=', 'chr%20', '%20chr', 'wget%20', '%20wget', 'wget(',
        'cmd=', '%20cmd', 'cmd%20', 'rush=', '%20rush', 'rush%20',
                   'union%20', '%20union', 'union(', 'union=', 'echr(', '%20echr', 'echr%20',
                   'echr=','esystem(', 'esystem%20', 'cp%20', '%20cp', 'cp(', 'mdir%20', 
                   '%20mdir', 'mdir(','mcd%20', 'mrd%20', 'rm%20', '%20mcd', '%20mrd', '%20rm',
                   'mcd(', 'mrd(', 'rm(', 'mcd=', 'mrd=', 'mv%20', 'rmdir%20', 'mv(', 'rmdir(',
                   'chmod(', 'chmod%20', '%20chmod', 'chmod(', 'chmod=', 'chown%20', 'chgrp%20', 
                   'chown(', 'chgrp(','locate%20', 'grep%20', 'locate(', 'grep(', 'diff%20',
                   'kill%20', 'kill(', 'killall','passwd%20', '%20passwd', 'passwd(', 
                   'telnet%20', 'vi(', 'vi%20','insert%20into', 'select%20', 'nigga(', 
                   '%20nigga', 'nigga%20', 'fopen', 'fwrite', '%20like', 'like%20',' $_request',
                   '$_get', '$request', '$get', '.system', 'HTTP_PHP', '&aim', '%20getenv', 
                   'getenv%20','new_password', '&icq','/etc/password','/etc/shadow', 
                   '/etc/groups', '/etc/gshadow','HTTP_USER_AGENT', 'HTTP_HOST', '/bin/ps', 
                   'wget%20', 'unamex20-a', '/usr/bin/id','/bin/echo', '/bin/kill', '/bin/',
                   '/chgrp', '/chown', '/usr/bin', 'g++', 'bin/python','bin/tclsh', 'bin/nasm',
                   'perl%20', 'traceroute%20', 'ping%20', '.pl', '/usr/X11R6/bin/xterm',
                   'lsof%20','/bin/mail', '.conf', 'motd%20', 'HTTP/1.', '.inc.php', 
                   'config.php', 'cgi-','.eml','file://', 'window.open', '<SCRIPT>',  
                   'javascript://','img src', 'img%20src','.jsp','ftp.exe','xp_enumdsn',
                   'xp_availablemedia', 'xp_filelist', 'xp_cmdshell', 'nc.exe',
                   '.htpasswd','servlet', '/etc/passwd', 'wwwacl', '~root', '~ftp', '.js',
                   '.jsp', 'admin_', '.history','bash_history', '.bash_history', '~nobody',
                   'server-info', 'server-status', 'reboot%20', 'halt%20','powerdown%20',
                   '/home/ftp', '/home/www', 'secure_site, ok', 'chunked', 'org.apache',
                   '/servlet/con','<script', '/robot.txt' ,'/perl' ,'mod_gzip_status',
                   'db_mysql.inc', '.inc', 'select%20from','select from', 'drop%20', 
                   '.system', 'getenv', 'http_', '_php', 'php_', 'phpinfo()', 
                   '<?php', '?>', 'sql=');


  $checkworm = str_replace($wormprotector, '*', $cracktrack);


  if ($cracktrack != $checkworm)
    {
      $cremotead = $_SERVER['REMOTE_ADDR'];
      $cuseragent = $_SERVER['HTTP_USER_AGENT'];


      header("location:$page");
      die();
    }
?>