Michael: Congratulo -
me com todos, sou Michael Lai, este é Matthew Richard, você pode chamá-lo de Matt ou Richard, porque ele tem dois nomes, mas isso não importa.
Matt: O tópico de nossa conversa hoje é ridículo de malware, e é exatamente isso que estamos tentando fazer.

Portanto, nem todo mundo que escreve o código faz isso bem, as pessoas cometem muitos erros. E nem todo mundo que usa o vírus faz certo. Também há pessoas que falham nesses dois casos. Portanto, sente-se com mais conforto, relaxe e ouça, talvez essa informação seja útil para você.
Por precaução, incluímos material técnico factual na apresentação para que você pelo menos aprenda algo se a conversa não lhe parecer engraçada. Observo que esta é apenas a nossa opinião, que pode não coincidir com a opinião de nossos empregadores.
Michael: A primeira história se chama "Querida, reduzi a entropia!" Ela fala sobre como o autor do Silent Banker, um algoritmo de criptografia muito complexo, esqueceu de criar entropia usando o PRNG - um gerador de números pseudo-aleatórios. No slide, você vê um snippet de código Zeus de setembro de 2007 no qual o PRNG é usado para impedir a detecção baseada em hash. A geração consiste em iniciar essa variável global chamada ddTickCount: primeiro, coloca-a no registro EAX, de onde a função é chamada pela primeira vez. Em seguida, é verificado se o valor da função é igual a zero e, se não for igual, o TickCount é chamado para gerar o SEED, ou seja, para iniciar um número pseudo-aleatório, usando o comando GetTickCount.

Não ficamos surpresos quando vimos as semelhanças com esse código no arquivo binário do Silent Banker de fevereiro de 2008. Ele usa o PRNG para gerar nomes de arquivos temporários. Aqui também existe a mesma variável global ddTickCount, que verifica se existe um zero e, se houver, um número pseudo-aleatório é iniciado usando GetTickCount. Primeiro, antes de ver o msvsrt rand, o gerador de números pseudo-aleatórios usado pela função rand () da biblioteca Microsoft C Runtime Windows, pensei que havia uma conexão entre o autor do Zeus e o autor do Silent Banker, apenas com base nos números HEX que foram codificados em um arquivo binário . Mas, na verdade, os dois estavam apenas estaticamente vinculados ao msvsrt.
Agora chegamos à receita do desastre. Este é um trecho de código da versão Silent Banker de julho de 2008, lançado alguns meses após a versão de fevereiro.

Eles atualizaram seu código e publicaram uma nova versão do Silent Banker, que era significativamente diferente do que vimos anteriormente. Neste programa, o PRNG é usado para gerar uma chave de criptografia. Aqui você não vê mais que uma variável global chamada CurrentSeed é verificada quanto à igualdade de zero e um número pseudo-aleatório é gerado dependendo disso, é simplesmente usado neste código.

É possível que em algum lugar do arquivo binário, mesmo antes deste local, o valor dessa variável global seja gerado na forma de algum tipo de número. Então, passo a desmontar esse código e ver se o valor CurrentSeed é usado em outro lugar do programa antes de ser usado nessa função rand (). Você vê que o dd inicialmente começa do zero e verificaremos as referências cruzadas para essa variável.

Na coluna T, o valor w significa que há apenas uma operação válida para essa variável global em todo o arquivo binário - esta é a própria função rand. Analisarei essas coisas fluentemente, porque elas já foram mencionadas no DefCon do ano passado. No slide “Receita para desastres”, a linha Semear o PRNG, ou “Iniciação de um gerador de números pseudo-aleatórios”, é mostrada em cinza para indicar que o autor do Silent Banker não fez essa iniciação.

O próximo passo é que eles gerem uma chave de 16 bytes, fazendo 1000 chamadas do sistema para a função MyRand (). Em seguida, a partir de uma chave de 16 bytes, eles geram um número de 8 bytes - a chave, usando uma fórmula específica.
Depois disso, eles geram outro número de 8 bytes para criar uma chave secundária a partir do primeiro número de 8 bytes, adicionam um valor arbitrário a partir do arquivo de configuração INI e obtêm uma chave terciária, que também é um número de 8 bytes. Finalmente, eles usam uma função matemática de precisão arbitrária para transformar uma chave de 8 bytes em uma de 32 bytes.
Depois disso, eles criptografam os dados roubados, como a senha do usuário, usando a chave original de 16 bytes. Mas eles não passam esse número de "16" bytes para o invasor "deles" com os dados roubados, porque enviar a chave junto com a mensagem criptografada não é uma boa ideia. Em vez disso, o autor do Silent Banker coloca um número de 32 bytes dentro dos dados roubados e o envia ao destinatário, que deve ter um programa que converta esse número de volta na chave original de 16 bytes. No entanto, não temos este programa!
O próximo slide mostra uma receita de como usar esse desastre com o número 1 - a falta de um gerador de PRNG - para sua vantagem.

Para começar, igualamos o valor de PRNG a zero. Podemos automatizar as próximas quatro etapas usando um script Python para o depurador, porque temos uma fórmula que calcula uma chave de 16 bytes, uma chave de 8 bytes, a próxima chave de 8 bytes e uma chave de 32 bytes. Essa fórmula não está no código C, mas a temos porque temos uma cópia do arquivo binário do Silent Banker no qual ela existe.
Vou mostrar uma demonstração de como esse script Python funciona. Temos um bom cenário: aqui tenho o Silent Banker e um depurador independente ao qual estou conectado, bem como o Internet Explorer, no qual o Silent Banker está sendo executado. Observei quatro recursos que geram chaves de criptografia. Eu incluo este script Python mostrado no slide anterior, que eu chamo com o comando bang keygen. Você pode ver que o depurador simplesmente "perde" essas poucas funções que eu quero executar para esta demonstração 5 vezes. Mas na vida real, realizamos essa ação 5.000 vezes para obter um conjunto maior de chaves.
No painel de log, você pode ver que, para cada iteração do loop, é emitida uma chave primária de 16 bytes, que é então associada a uma chave de 32 bytes. Ao mesmo tempo em que o script imprime informações no log, também é criado um arquivo de texto no disco, que inclui pares de chaves relacionadas de 16 e 32 bytes. É apenas um arquivo hexadecimal HEX, para que possamos usar nosso script Python para processar esse arquivo, também temos um diretório de log que recuperamos do nó de comando e controle roubado.

Na parte superior, você vê vários certificados de chaves privadas criptografadas e, abaixo deles, vários arquivos de texto que contêm dados criptografados. Podemos simplesmente executar o programa e pesquisar dentro desses arquivos de texto extraindo essa chave de 32 bytes e a chave original de 16 bytes associada a ele.
Assim que o programa encontra uma chave de 16 bytes, descriptografa as informações nele contidas e as apresenta na forma de um arquivo de texto. Você vê esse arquivo na tela e é impossível lê-lo.

Mas temos um monte de arquivos temporários .tmp legíveis, de onde podemos obter essas informações e devolvê-las aos proprietários "legítimos". Portanto, todo o trabalho duro para proteger as informações foi realizado em vão pelo Silent Banker, porque eles esqueceram de iniciar um gerador de números pseudo-aleatórios.

Agora vou mostrar a melhor parte do exposto acima - esta é a função Silent Banker, que chamei de Why_Not_Use_This (por que não usá-la?).

De fato, dentro de seu próprio programa, eles têm a função GetCursorPos (determinar a posição do cursor) para gerar entropia, que pode ser usada para iniciar o PRNG, e podemos verificar referências cruzadas para essa função dentro do programa.

Vemos que ele é usado em 10 a 15 outros lugares no código. Assim, verifica-se que os autores do Silent Banker não esqueceram de inserir um gerador de números pseudo-aleatórios no programa, simplesmente esqueceram de executar essa função no processo de criptografia usando o operador de chamada.

O próximo slide é chamado "Isso escapou ..." e mostra como esse programa funcionaria se o autor não tivesse esquecido nada.

A próxima história, intitulada "DES ou não DES", é sobre um autor de malware que nem sabe como usar adequadamente a interface de programação do Windows ou não sabe qual é o tamanho máximo da chave DES. Como resultado, devido ao tamanho inválido dessa chave, seu Trojan é usado por padrão com o operador lógico xor.
Portanto, para a função de interface do programa CryptDeriveKey, os dois bytes baixos do parâmetro dwFlags, sinalizadores que definem a aparência da URL resultante, determinam o tamanho da sua chave de criptografia.

Portanto, se os bytes baixos forem 0080, a chave de criptografia solicitada será uma chave RC4 de 128 bits. É o mesmo que dar um tiro no próprio pé, e eu vou lhe mostrar o porquê.

No slide, você vê uma linha com o tamanho errado da chave dwFlags de 128 bits - 800000 e uma linha com o valor incorreto do MSCryptoAPI. Eu vou te mostrar a desmontagem dessa coisa. Você vê uma função chamada “inicialização do subsistema de criptografia”: o trojan chama o contexto criptografado e cria um contêiner para o hash MD5, após o qual cria um hash MD5 da senha codificada no arquivo binário e tenta usar a saída dessa função hash para criar uma chave DES de 128 bits. No entanto, nenhuma chave é criada nesse caso, porque não existe uma chave DES de 128 bits.

Se alguma dessas funções da API falhar, ela pula para este local, que eu marquei em amarelo, e exibe uma mensagem de que a chave não pode ser recebida. E este lugar é aqui, onde ele move o valor que está em ebp e naquele momento é 0, ou seja, diretamente para esse valor booleano bUseMSCryptoAPI.
Vamos ver o efeito que isso causa durante a execução do programa. Seguiremos esse elemento da estrutura de código para ver onde mais ele é usado no programa e quão diferente esse trojan exibe se comporta quando a função é verdadeira e quando a ferida é falsa.

Vemos que o valor lógico é verificado na função que chamei de criptografar dados, “criptografia de dados” e, se for verdade, chega a esse bloco, onde são usadas a criptografia DES e o MSAPI CryptEncrypt.

No entanto, se esse valor for 0 e, como sabemos, sempre será zero, a função vai para esse bloco, que por padrão é xor.

Fiquei curioso para saber em que momento o autor do programa malicioso decidiu fazer backup de tudo isso. Talvez as pessoas o pressionassem de cima para baixo, então ele foi forçado a se livrar do malware, mas no último minuto ele percebeu que seu DES não funcionava, então ele usou o xor para gravação de backup. No geral, foi bem engraçado, então a moral dessa história é sempre fazer backups!
A história a seguir é chamada "O que você fez com o quê?". Tentei criar um termo que descrevesse como a criptografia do Trojan Coreflood funciona e decidi chamá-lo de "criptografia dependente da localização". Em suma, os autores deste Trojan inventaram um novo método de criptografia. Eu pensei, talvez alguém já tenha escrito um artigo sobre isso e deveria ser "google"? O Google me deu um link para um site de patentes nos EUA onde alguém registrou uma patente para "criptografia dependente da localização". Esse esquema é bastante confuso, portanto levará muito tempo para estudá-lo. Eis como funciona: Estou enviando uma mensagem criptografada e, para decifrá-la e lê-la, você precisa pegar um dispositivo GPS e ir até um ponto com a latitude e longitude indicadas por mim. Normalmente, a criptografia é um compromisso entre segurança e usabilidade, mas não existe um nem outro nesse método.

Definitivamente, isso não é seguro e exige que você vá para onde o remetente aponta para ler a mensagem. Matt brincou dizendo que, se você está lutando online por e-mail e realmente quer se livrar de alguém, envie a ele uma mensagem criptografada que ele pode ler em algum lugar do Iraque e você não terá mais problemas com ele.
Como esse método é usado no Trojan Coreflood? O slide mostra um fragmento de código do qual se conclui que, após o cavalo de Troia ter roubado informações do usuário, ele é criptografado e gravado no disco para que o cavalo de Tróia possa posteriormente receber essas informações e fazer upload de comando e controle em seu site.
Essa função é chamada SetFilePointer (define o ponteiro do arquivo) e seu valor de retorno é dWord, indicando o deslocamento no arquivo no qual o ponteiro foi definido, se excedido. Em seguida, a função pega o número de bytes para criptografar nNumberOfBitesToWrite e o move para o registro ecx. Ela então pega o ponteiro de dados para criptografia e o move para o registro edx.

Depois disso, é utilizado o operador xor, que coloca cada byte no buffer al e ah, o que significa bytes de nível alto e baixo retornados do SetFilePointer. Portanto, a chave de criptografia nesse esquema é o deslocamento no arquivo em que os dados existem. Isso é incrível!
O próximo slide é chamado "Como redefinir um dump principal". Ele descreve o programa dumpCore que acabei de escrever, que acabou de sair. Você pode baixá-lo, existe todo o código fonte. Este programa ajudará você se o computador estiver infectado com o vírus Coreflood, que por algum motivo não pôde acessar o servidor de comando e controle para baixar os dados roubados. Para que você possa obter esses arquivos que ele salvou em disco e descriptografá-los usando o meu programa para descobrir o que foi roubado de você, por exemplo, se precisar informar o cliente sobre isso.
Os registros dos dados roubados estão circulados em vermelho no slide.

O que ainda é interessante no Coreflood: embora tenha um algoritmo de criptografia bastante fraco, ele ainda tenta transferir todas as informações roubadas sobre a configuração do computador da vítima, todas as informações de destino de bancos e cooperativas de crédito e assim por diante. Portanto, outra maneira de remover um core dump é chamada "Como remover um core dump usando o Wireshark". O Wireshark é um programa que analisa o tráfego da rede Ethernet ou o fluxo de dados TCP.

O slide a seguir mostra como o Coreflood funciona. Essas são dlls inseridas no Explorer e no Internet Explorer. Eles modificam o registro, exigem uma reinicialização do aplicativo, mas não requerem uma reinicialização do sistema. Existem várias maneiras de injetar essas DLLs em um processo.

Importante para os hackers que desejam invadir o vírus despercebido é como o vírus entra no computador do usuário: requer uma reinicialização do sistema para que o malware tenha efeito ou é suficiente que o usuário simplesmente reinicie o aplicativo, neste caso o Explorer.
E agora está quieto para que ninguém possa ouvir!

Este é o código que reconstruímos usando engenharia reversa. Isso mostra como o Coreflood desliga manualmente o Explorer para que as alterações entrem em vigor imediatamente. Você provavelmente está familiarizado com o que acontece quando o Explorer falha no computador - a barra de tarefas desaparece, as janelas de todos os aplicativos abertos, todos os ícones na área de trabalho desaparecem e, um a um, eles começam a voltar ao seu lugar.
Os autores do Coreflood obviamente sabiam disso, então fizeram uma chamada de sistema neste local para definir o modo de erro "correto" do condutor logo antes da chamada do OpenProcess.
O que a função SetErrorMode faz? Evita uma falha específica das notificações enviadas ao sistema que criam uma pequena janela pop-up e enviam uma mensagem de erro que levou ao encerramento do aplicativo. Tudo o que fizeram com essa mensagem de erro foi impedir que uma janela pop-up aparecesse para o usuário antes da falha do Explorer. Diga-me o que parece mais suspeito para o usuário: uma pequena janela pop-up acompanhada pelo desaparecimento de tudo o que aparece na tela e depois reaparece, ou o desaparecimento e a aparência de tudo sem nenhuma mensagem de erro? Ouvi você dizer: "ambos os eventos".
No próximo slide, chamei "Com braços e pernas, mas sem cabeça". O Coreflood, quando carregado como uma DLL, não aparece na lista de módulos carregados. Ele aloca um pouco de memória na pilha e se copia para esse local - eu coloco em uma moldura vermelha.

Em seguida, ele exclui o cabeçalho do PE. Portanto, se você encontrar um computador infectado com esse cavalo de Troia, diga: "minha próxima etapa deve despejar esse arquivo executável e enviá-lo ao IDA para análise", mas é muito difícil despejar o arquivo executável se não houver seu cabeçalho PE. Portanto, quando o Coreflood chama alocação virtual, define o sinalizador mem de cima para baixo, o que faz com que o sistema retorne o endereço mais alto, e não o mais baixo disponível. Isso permite que o Trojan oculte as aspas de abertura / fechamento em uma área de memória mais alta do modo de usuário entre outras DLLs do sistema. Portanto, na próxima demonstração, chamei "Como tornar inútil tudo o que está oculto".

Quando você se deparar com algo como o Coreflood, que usa furtividade, e não há ferramentas prontas para trabalhar com esses vírus, você deve criar o seu.
Se você estiver familiarizado com a descompactação, é comum usar um depurador. Especialmente se não houver desempacotador automático, pois esse não é um algoritmo comum. Nesse caso, você pode usar o depurador para ir para o ponto de entrada original e remover o despejo do Trojan usando ProcDump ou outro utilitário. PE Import Reconstructor, , , .
, . . Volatility, Internet Explorer . , Coreflood, , . , 7FF81000.

, HEX , Coreflood. , , . .
, , Coreflood, Volatility . , ID Internet Explorer. , , PID 1732. Malfind, , , , . VAD , , . , .

, , 7FF81000. , Fix IAT, PID 1732 Internet Explorer , Coreflood.
dll, Internet Explorer, , RBA , , .
, 7FF81000, , . , PE . , Import Reconstructor: , , . Fix IAT , PE modify viewer , .

21:15
DEFCON 17. ! Parte 2Obrigado por ficar conosco. Você gosta dos nossos artigos? Deseja ver materiais mais interessantes? Ajude-nos fazendo um pedido ou recomendando a seus amigos, um
desconto de 30% para os usuários da Habr em um análogo exclusivo de servidores básicos que inventamos para você: Toda a verdade sobre o VPS (KVM) E5-2650 v4 (6 núcleos) 10GB DDR4 240GB SSD 1Gbps de US $ 20 ou como dividir o servidor? (as opções estão disponíveis com RAID1 e RAID10, até 24 núcleos e até 40GB DDR4).
VPS (KVM) E5-2650 v4 (6 núcleos) 10GB DDR4 240GB SSD de 1Gbps até dezembro de graça quando pagar por um período de seis meses, você pode fazer o pedido
aqui .
Dell R730xd 2 vezes mais barato? Somente nós temos
2 TVs Intel Dodeca-Core Xeon E5-2650v4 128GB DDR4 6x480GB SSD 1Gbps 100 a partir de US $ 249 na Holanda e nos EUA! Leia sobre
Como criar um prédio de infraestrutura. classe usando servidores Dell R730xd E5-2650 v4 custando 9.000 euros por um centavo?