
Davide Cavallini:15 Novembro 2025 15:55
Bom dia a todos. Eu sou Davide Cavallini, um desenvolvedor web e testador de penetração. Hoje vou falar sobre injeções. Existem vários tipos, mas o que conceitualmente significa injetar? Já pensei sobre isso, e acho que tenho uma resposta universal.
Injeções explicadas de forma simples
Vamos pegar um exemplo simples. Temos um pedido para enviar ao município para obter um certificado.
O formulário de solicitação é o seguinte:
Il sottoscritto __________________________ richiede il certificato di residenza al comune di Casaccio.
Normalmente, o formulário deve ser preenchido escrevendo seu nome no espaço disponível.
O próprio nome, no jargão da computação, é definido como ” parâmetro “, pois é justamente um parâmetro variável que varia a solicitação de acordo com nossas necessidades.
Ao inserir o nome ” Davide ” como parâmetro, solicitaremos o certificado de Davide ao escritório.
Mas e se o próprio parâmetro alterar a estrutura da solicitação?
Vamos tentar escrever a seguinte frase destacada no espaço em branco:
Il sottoscritto Antonio assieme con il sottoscritto Davide richiede il certificato di residenza al comune di Casaccio
Neste momento, o município, recebendo este pedido, e assumindo que tem um funcionário sem capacidade de raciocínio, como os computadores (não) têm, nos daria dois documentos, tanto de Antonio quanto de Davide.
O espaço não filtrado a ser preenchido, neste caso pelo funcionário, Assim, se revelaria como uma vulnerabilidade a pedidos fáceis que não seriam apropriados para nós.
A mesma frase” Antonio junto com ” seria definido em linguagem de “computador” como ” Carga útil ”.
Vejamos tudo isso de uma perspectiva de banco de dados
A mesma coisa pode acontecer em bancos de dados, mas ainda estamos no mundo abstrato. Se tivéssemos um banco de dados que recuperasse os endereços de um usuário de uma tabela com base no id passado como parâmetro, a solicitação seria algo assim:
PRENDI IL DATO DELL'UTENTE DALLA TABELLA “UTENTI” DOVE L'ID E' UGUALE AL PARAMETRO ID APPENA PASSATO
Se o parâmetro ID fosse “1”, os dados do usuário com ID 1 seriam extraídos da tabela.
Mas e se mudássemos o id que passamos para a solicitação assim?
PRENDI IL DATO DELL'UTENTE DALLA TABELLA “UTENTI” DOVE L'ID E' UGUALE A QUALSIASI ID
Nesse caso, a página pode nos mostrar os dados de todos os usuários contidos no banco de dados.
Em uma situação real, a solicitação SQL pode ser:
select * from users where id=$_GET['id'];
Contanto que o $_GET[‘id’] parâmetro é igual a um número, não há problema, pois a consulta seria a seguinte: No exemplo vamos passar: $_GET[‘id’] = 1
SELECT * FROM `users` WHERE id=1;
Mas e se o $_GET[‘id’] Eram iguais a ID (condição sempre verdadeira)? Nesse caso, receberíamos todos os dados do usuário de volta.
Na verdade, ao escrever a consulta:
SELECT * FROM `users` WHERE id=id;
Receberemos todos os resultados dos usuários de volta.
Além dos usuários…
Neste ponto, parece que não seríamos capazes de obter nenhum outro dado do banco de dados além dos usuários, mas ESSE NÃO É O CASO.
Existem outros comandos SQL que podem realmente nos permitir extrair outros dados, sabendo quantos campos são extraídos da tabela na qual a consulta original é feita.
Uma maneira simples de testar quantas colunas você pode extrair é fazer um “UNION SELECT” tentando inserir um número cada vez maior de colunas.
Exemplo:
$_GET['id']=1 union select 1 - -
$_GET['id']=1 union select 91827364,91827364 - -
$_GET['id']=1 union select 91827364,91827364,91827364 - -
$_GET['id']=1 union select 91827364,91827364,91827364,91827364 - -
$_GET['id']=1 union select 91827364,91827364,91827364,91827364,91827364 - -
Se a primeira seleção (dos usuários) tiver 5 colunas, quando você chegar nessa última seleção de união, o número 91827364 aparecerá em algum lugar da página.
Neste ponto, poderíamos, por exemplo, substituir o número 91827364 pela função version() e ver a versão do banco de dados, ou fazer uma subseleção para ver dados de outras tabelas, como
1 union select 1,2,3,4,( select password from secret);
OU TAMBÉM
1 union select 1,2,3,4,( select concat(username,999, password ) from secret);
Em casos mais graves, o atacante também pode truncar a tabela (excluí-la completamente), inserir e modificar dados ou criar shells remotos no servidor onde podem executar código arbitrário.
Conclusões
As injeções de banco de dados são um problema muito sério para as empresas, e ainda estão muito presentes em sites, ou em alguns plugins ou temas vulneráveis, mas não são o único tipo de injeção possível.
Na verdade, existem outros tipos de injeção que podem permitir a execução de comandos remotos, ou a inserção de Javascript ou HTML na página.
As empresas devem sempre ter muito cuidado ao desenvolver um aplicativo da web.
É importante trabalhar com programadores competentes que validam o código com ferramentas como PHPstan, LARAstan, SonarCube e outros validadores estáticos, e que tenham pelo menos um conhecimento básico de segurança cibernética. Portanto, é importantent para entender como os ataques cibernéticos ocorrem para que você possa evitá-los.
É igualmente importante ter aplicativos testados em um ambiente de “pentesting” por alguém que lida com hacking ético profissional.
Davide Cavallini
Davide Cavallini é um desenvolvedor sênior especialista em Laravel e JavaScript, com experiência significativa como testador de penetração. Sua carreira é marcada pelo compromisso de ensinar e compartilhar seus conhecimentos, contribuindo para a formação de novos profissionais em desenvolvimento de software e cibersegurança. Sua paixão pela tecnologia o leva a se manter atualizado e explorar novas fronteiras na computação.