Na vastidão da rede, nosso pod foi encontrado. Isso é crackme . Naturalmente, é necessário estudá-lo. Para a autópsia, precisamos:
- Um pouco de Assembler
- Lógica com depurador (IDA PRO)
Vamos fazer um remédio

Este crackme não é muito complicado. Considere o algoritmo para gerar uma chave na chave correta 8365-5794-2566-0817 . No IDA Pro, adicionei comentários sobre o código.
Exame do paciente
À primeira vista, o comportamento é normal. Extensão .Exe. Não embalado. Vamos começar.


O que é isso? Requer uma chave. Precisa curar :)
Autópsia do paciente
Se houvesse um erro, havia uma inscrição “Fail, Serial is invalid!”. Tomemos um lugar onde ele é usado no programa.

Vemos 1 função key_check_func antes do desvio condicional. Vamos examiná-la.
Uma árvore interessante aparece.

Definimos um ponto de interrupção e iniciamos a depuração.
A chave deve ter 19 caracteres.

Em seguida, o programa verifica a presença de um travessão na chave a cada 5 caracteres, entrando no loop 3 vezes.


Depois de verificar a presença de um travessão, o programa examina se o bloco de teclas (tecla 1/4) consiste em números. Existe uma suposição para entender qual dígito foi passado para o compilador executando o comando.
add eax, 0FFFFFFD0h

Por exemplo, adicione 8 (38h) com o número fornecido. O número resultante é muito grande ( 10000008h) e no final é 8, portanto, é cortado. Permanece 8. Este é o valor que demos. Isso acontece 4 vezes em um ciclo.

O que agora? Hoje em dia, os códigos de cada dígito do bloco verificado são somados, mas os 4 últimos dígitos são somados 3 vezes seguidas. O valor resultante é adicionado novamente. O código do último dígito do bloco + a quantidade resultante é 150h. O resultado é adicionado a r10d. Todo este ciclo é repetido 4 vezes para cada bloco de teclas.

Em nosso caso, considere o exemplo do primeiro bloco da chave 8365: 38h (8) + 33h (3) + 36h (6) + 35h (5) + 35h (5) + 35h (5) = 140h + 35h - 150h = 25h. 25 é adicionado a r10d e gravado na memória. Vamos marcar este local como A. A soma dos outros blocos da chave também é igual a 25h. Portanto, multiplicamos 25h * 4 = 94.
Em seguida, ocorre um deslocamento bit a bit para a direita de 2 bytes. Vamos marcar este local para nós como B.

Temos um valor designado como A (25h) e B (25h). Posteriormente, esses números serão comparados. Eles devem ser os mesmos. Esta operação ocorre para cada bloco de teclas.

A última coisa que o programa faz é verificar se os números nos blocos são semelhantes. Primeiro, os dígitos do 1º bloco são comparados com os dígitos do 2º bloco. Em seguida, verifique 2 blocos com 3 blocos. Verificação final 3 blocos com 4 blocos. Toda essa verificação não acontece imediatamente, mas gradualmente em um ciclo.


A análise acabou. O paciente foi estudado.
Hora de uma cura
Usaremos algo incomum para gerar a chave. Python + Biblioteca aleatória.
O código em si está abaixo. Comentários no código:
import random
def gen_key_part():
#
num1 = str(random.randint(0, 9))
num2 = str(random.randint(0, 9))
num3 = str(random.randint(0, 9))
num4 = str(random.randint(0, 9))
# (1 )
final = num1 + num2 + num3 + num4
return final
def sum_ord(key_part):
#
num1 = key_part[0]
num2 = key_part[1]
num3 = key_part[2]
num4 = key_part[3]
# crackme
sum = ord(num1) + ord(num2) + ord(num3) + ord(num4) + ord(num4) + ord(num4)
sum_final = ord(num4) + sum - 336
return sum_final
def shr(key):
#
a = key[0:4]
b = key[5:9]
c = key[10:14]
d = key[15:19]
# crackme
x = sum_ord(a) + sum_ord(b) + sum_ord(c) + sum_ord(d)
x = x >> 2
return x
def check_key(key):
i = 0 #
while i != 4:
# i 1 4.
first = 0 + i
second = 5 + i
third = 10 + i
four = 15 + i
# ( , A B)
if sum_ord(key[0:4]) != shr(key) or sum_ord(key[5:9]) != shr(key) or sum_ord(key[10:14]) != shr(key) or sum_ord(key[15:19]) != shr(key):
return False
#
if int(key[first]) == int(key[second]):
return False
if int(key[second]) == int(key[third]):
return False
if int(key[third]) == int(key[four]):
return False
i += 1 # #
def generate_key():
#
key = gen_key_part() + '-' + gen_key_part() + '-' + gen_key_part() + '-' + gen_key_part()
# true false
while True: #
if check_key(key) == False:
#
key = gen_key_part() + '-' + gen_key_part() + '-' + gen_key_part() + '-' + gen_key_part()
print('Checking this key -> ' + key)
else:
#
print('This is the correct key -> ' + key)
break
# ,
if __name__ == "__main__":
generate_key()
Nós lançamos.

Digite a chave e veja.

O paciente está curado.
Obrigado pela atenção. Aguardo seus comentários e críticas. Não fique doente.