VDRegister |
||
Data |
by "DesTroYer" |
|
11/June/2006 |
Published by Quequero |
|
TO EXPECT THE UNEXPECTED |
Splendido tute, grazie destr! |
|
.... |
|
.... |
Difficoltà |
(X)NewBies ( )Intermedio ( )Avanzato ( )Master |
Introduzione |
VdRegister è un’applicazione esterna al programma vero e proprio che ha il solo scopo di permettere la registrazione dello stesso. Tralascio di proposito di parlare del programma principale perché, in effetti, tutto quello che ci serve sta proprio in questa applicazione. Il tipo di protezione che andiamo ad affrontare è comune a molti programmi commerciali che utilizzano, infatti, dei programmi esterni con maschere per l’inserimento dei dati per la registrazione, e cioè richiede l’inserimento del nome, cognome e a fronte di un codice che ci fornisce il programma stesso (per permettere la codifica del seriale esatto), l’inserimento del nostro seriale.
Tools usati |
Peid Con pluginn KryptoANALyzer (Da usare sempre prima di iniziare qualunque analisi)
OllyDbg (Ottimo debugger)
Tabella Codici ASCII (serve, serve J))))
URL o FTP del programma |
Il programma puo essere scaricato qui
Notizie sul tipo di protezione |
Al lancio il programma crea nella stessa directory un file chiamato VDKey.xxx all’interno del quale, nella fase iniziale, troviamo il Serial Number criptato che ci viene fornito e che poi verrà usato per generare il Key Code per la registrazione. Inoltre è necessario che sia l’eseguibile che il VDKey siano sotto la stessa directory che deve avere il nome di gauges. Infine se noi cancelliamo il VDKey il programma lo ricrea al lancio con un nuovo codice.
Essay |
Iniziamo subito.
Per prima cosa è mia abitudine analizzare il file con PeiD per sapere con chi avremo a che fare e che tipo di compressione eventualmente usa oltre ad una serie di informazioni che potrebbero esserci utili.
Subito vediamo che non è compresso e che il linguaggio di programmazione utilizzato è il Visual C++ 6.0.
Facciamolo analizzare anche da KryptoANALyzer andiamo in plugins e vediamo che il programma non usa nessun tipo di criptazione.
Lanciamo il programma e cominciamo a studiarlo. Il solito nome e cognome da inserire, il seriale calcolato automaticamente dal programma e il nostro codice da inserire. Bene non inseriamo niente, premiamo Register e vediamo cosa succede.
Notiamo subito che il programma fa un controllo sul primo nome, sul secondo e sul Key Code che devono essere inseriti.
Lanciamo il programma inseriamo i nostri dati fasulli (io ho inserito PIPPO, PLUTO e 1234ABC)
Premiamo Register subito compare un form che ci dice come deve essere formato codice (nnnnlll con n = number e l = carattere maiuscolo) ……………………………………………….Notizia molto interessante
Reinseriamo il tutto come dice il programma
Premiamo Register e subito, se
non siamo fortunati ma a quel punto io giocherei
al lotto,
Lanciamo Olly e carichiamo il programma da analizzare, tasto destro e andiamo a cercare la stringa che abbiamo precedentemente segnato. Subito la fortuna o qualcos’altro ci da una mano; troviamo una bella stringa che ci ringrazia per la registrazione. Non facciamoci però strane illusioni, abbiamo detto che dobbiamo trovare il codice, e poi se cambiamo il jump il programma non funziona lo stesso. …………Eh! Eh! Eh!……….:))))))
Andiamo invece a cercare la nostra bella stringa “Your key code is not valid…..” e la troviamo alla linea 401BCE.
Saliamo un poco e troviamo subito i salti che portano all'errore basta posizionarsi sulla linea 401BC8 che è dove inizia il messaggio di errore e li vediamo nella Disassembler Window in basso; sono 4 (quattro). Prendiamo nota.
00401BC8 PUSH EBP 00401BC9 PUSH 00409998 ; ASCII "Error" 00401BCE PUSH 004093C8 ; ASCII "Your key code is not valid (Be careful of letter case\rand key format : nnnnlll with n=numbers & l=upper-case letters).\r\rVotre clé n'est pas valide (Attention à la casse des lettres\ret au format de la clé : nnnnlll avec n=chiffres et "... 00401BD3 JMP 004013A5 00401BD8 MOV ECX,40 00401BDD MOV EAX,30303030 00401BE2 MOV EDI,0040A824 00401BE7 REP STOS DWORD PTR ES:[EDI] 00401BE9 XOR ECX,ECX 00401BEB MOV EAX,0040A825 00401BF0 MOV BL,DS:[ECX+40A9A4] 00401BF6 OR DL,0FF 00401BF9 SUB DL,BL 00401BFB MOV BL,DS:[ECX+40A9E4] 00401C01 MOV DS:[EAX-1],DL 00401C04 OR DL,0FF 00401C07 SUB DL,BL 00401C09 MOV BL,DS:[ECX+40A964] 00401C0F MOV DS:[EAX],DL 00401C11 OR DL,0FF |
Jumps from 00401AD0, 00401B20, 00401B5A, 00401B90
Inseriamo dei BP agli indirizzi precedentemente trovati e rilanciamolo (F9), inseriamo i dati fasulli ( Io ho inserito pippo – pluto e 1234ABC) premiamo Register e….subito Olly brekka al primo Breakpoint inserito alla linea 401AD0 ed è dove noi troviamo il JNZ che ci fa saltare alla MessageBox di codice fasullo. Bene risaliamo il codice fin dove inizia l’algoritmo di calcolo e precisamente alla linea 401A5C
00401A5C MOV ESI,DWORD PTR DS:[408070] INIZIO ALGORITMO CALCOLO SERIALE 00401A62 PUSH 3 00401A64 LEA EDX,DWORD PTR SS:[ESP+14] 00401A68 PUSH 40A964 ; |String2 = "2375-PDMV-423096" SERIAL DEL PROGRAMMA IN CHIARO 00401A6D PUSH EDX VIENE PUSHATO NELLO STACK 00401A6E MOV DWORD PTR SS:[ESP+1C],EBP 00401A72 CALL ESI CALL DI CONTROLLO DEL SERIALE (SE CI SONO SPAZI O CARATTERI SPEIALI ETC.) 00401A74 LEA EAX,DWORD PTR SS:[ESP+10] CARICA IN EAX I PRIMI DUE CARATTERI NUMERICI (23) DEL SERIALE DATO DAL PRG 00401A78 PUSH EAX VIENE PUSHATO 00401A79 CALL 0040253B CALL CHE TRASFORMA I CARATTERI PRESI IN ESADECIMALE (23 = HEX 17) E LO METTE IN EAX ALL’USCITA 00401A7E ADD ESP,4 00401A81 LEA ECX,DWORD PTR SS:[ESP+10] CARICA IN ECX I DUE CARATTERI PRESI (23) 00401A85 MOV EDI,EAX METTI IN EDI IL VALORE DI EAX (17) 00401A87 MOV DWORD PTR SS:[ESP+10],EBP AZZERA 00401A8B PUSH 3 00401A8D PUSH 40A966 ;ASCII "75-PDMV-423096" PUSHA IL RIMANENTE CODICE 00401A92 PUSH ECX 00401A93 CALL ESI 00401A95 LEA EDX,DWORD PTR SS:[ESP+10] CARICA IN EDX IL 3° E 4° CARATTERE NUMERICO DATO DAL PROGRAMMA (75) 00401A99 PUSH EDX LO PUSHA 00401A9A CALL 0040253B E LO TRASFORMA IN ESADECIMALE (4B) 00401A9F ADD ESP,4 00401AA2 MOV EBX,EAX LO MUOVE IN EBX 00401AA4 LEA EAX,DWORD PTR SS:[ESP+10] CARICA IN EAX I DUE NUMERI PRESI (75) 00401AA8 MOV DWORD PTR SS:[ESP+10],EBP AZZERA 00401AAC PUSH 3 00401AAE PUSH 40A926 ; ASCII "34ABC" PUSHA IL RIMANENTE CODICE DA ME INSERITO 00401AB3 PUSH EAX 00401AB4 CALL ESI 00401AB6 LEA ECX,DWORD PTR SS:[ESP+10] CARICA IN ECX IL MIO 3° E 4° CARATTERE (34) 00401ABA PUSH ECX LO PUSHA NELLO STACK 00401ABB CALL 0040253B LO TRASFORMA IN ESADECIMALE (22 HEX) 00401AC0 MOV ECX,EAX MUOVE IL 3° E 4° CARATTERE DEL SERIAL
DATO DAL PRG IN ECX (4B IN HEX = 00401AC2 MOV EAX,EDI MUOVE IL 1° E IL 2° CARATTERE DEL SERIAL
DATO DAL PRG IN EAX ( 00401AC4 SUB EAX,EBX SOTTRAE AL 1° E 2° CARATTERE IL 3° E 4° CARATTERE DEL SERIAL DATO DAL PRG (17 - 4B = FFFFFFCC) 00401AC6 ADD ESP,4 00401AC9 CDQ 00401ACA XOR EAX,EDX XORA EAX CON EDX (FFFFFFCC XOR FFFFFFFF= 33) 00401ACC SUB EAX,EDX SOTTRAI EDX AD EAX (33 - FFFFFFFF = 34) 00401ACE CMP EAX,ECX COMPARA IL NOSTRO 3° E 4° CARATTERE (IN HEX) CON QUELLO CALCOLATO (EAX = 52 ECX = 34) 00401AD0 JNZ 00401BC8 SE NON E’ UGUALE SALTA AL MESSAGGIO DI ERRORE |
Quindi il CMP alla linea 401ACE non fa altro che verificare che una parte del codice inserito sia uguale ad una parte del codice esatto che è stato calcolato. Risaliamo un attimo il codice e ci accorgiamo subito dove viene preso una parte del seriale del prg e precisamente alla linea 401A5C che è dove inizia la routine di calcolo, vediamo cosa ne fa; togliamo tutti i BP e ne mettiamo uno direttamente alla linea 401A5C.
Cominciamo a steppare ed a capire l’algoritmo di calcolo del seriale esatto. ( Ho inserito le note a fianco per capire come viene effettuato il calcolo del seriale). Arrivati alla linea 401ACE c’è il primo controllo dove viene controllato se EAX (parte di seriale calcolato dal programma) è uguale a ECX (nostra parte di seriale inserito), se non sono uguali salta alla MessageBox di errore. Quindi dobbiamo fare in modo che ECX sia uguale a EAX, vediamo come…. continuiamo.
Scendiamo fino al CMP e vediamo che ECX = 22 (nel mio caso)
viene comparato con EAX = 52.Cosa è quel
Deduzione logica
Se EAX = 52 , anche ECX deve essere
uguale a 52 EH! EH! EH! come sono
spiritoso per non
saltare all’errore. Questo vuol dire che il terzo e quarto numero deve essere
Proviamo ad inserire al posto di 34 il valore 52 e vedete che il CMP sarà esatto quindi il programma continua sequenzialmente. Primo step passato.
Continuiamo nello stesso modo ,alla linea 401AD6 inizia il nuovo calcolo, vengono presi il primo e secondo numero che noi abbiamo inserito e cioè 1 e 2 e dopo aver fatto altri calcoli spiegati sotto, EAX esce con C cioè 12 .
00401AD6 PUSH 3 00401AD8 LEA EDX,DWORD PTR SS:[ESP+14] VIENE CARICATO IN EDX IL 3°E 4° CARATTERE INSERITO (52) 00401ADC PUSH 40A924 ; ASCII "1252ABC" 00401AE1 PUSH EDX VIENE PUSHATO NELLO STACK 00401AE2 MOV DWORD PTR SS:[ESP+1C],EBP AZZERA 00401AE6 CALL ESI 00401AE8 LEA EAX,DWORD PTR SS:[ESP+10] VIENE CARICATO IN EAX IL 1° E 2° CARATTERE DEL MIO SERIAL INSERITO (12 DEC) 00401AEC PUSH EAX VIENE PUSHATO 00401AED CALL 0040253B CALL CHE TRASFORMA I CARATTERI PRESI IN ESADECIMALE (12 = HEX C) E LO METTE IN EAX ALL’USCITA 00401AF2 MOVSX EDX,BYTE PTR DS:[40A96C] MUOVE IN EDX IL 9° CARATTERE DEL SERIAL DEL PRG IN HEX (V = 56 HEX) 00401AF9 MOV ECX,EAX SPOSTA IN ECX IL NOSTRO 1° E 2° CARATTERE (C) 00401AFB ADD ESP,4 00401AFE MOVSX EAX,BYTE PTR DS:[40A96B] MUOVE IN EAX L’8° CARATTERE DEL SERIAL DEL PRG IN HEX ( M = 4D HEX) 00401B05 SUB EAX,EDX SOTTRAE EDX AD EAX (56-4D = FFFFFFF7) 00401B07 MOVSX EDX,BYTE PTR DS:[40A96A] MUOVE IN EDX IL 7° CARATTERE DEL SERIAL DEL PRG IN HEX ( D = 44 HEX) 00401B0E SUB EAX,EDX SOTTRAE EDX AD EAX (FFFFFFF7 - 44 = FFFFFFB3) 00401B10 MOVSX EDX,BYTE PTR DS:[40A969] MUOVE IN EDX IL 6° CARATTERE DEL SERIAL DEL PRG IN HEX ( P = 50 HEX) 00401B17 ADD EAX,EDX SOMMA EDX AD EAX (FFFFFFB3 + 50 = 03) 00401B19 CDQ 00401B1A XOR EAX,EDX XORA EAX CON EDX (EAX = 3 E EDX = 0) 00401B1C SUB EAX,EDX SOTTRAI EDX AD EAX (3-0 = 3) 00401B1E CMP EAX,ECX COMPARA IL NOSTRO 1° E 2° CARATTERE (IN ESADECIMALE)CON QUELLO CALCOLATO (12 CON 03) 00401B20 JNZ 00401BC8 SE NON E’ UGUALE SALTA AL MESSAGGIO DI ERRORE |
A questo punto abbiamo capito cosa fare e cioè sostituire al nostro primo e secondo carattere con quello ottenuto e cioè 03. Facciamolo e vediamo che anche il secondo step è superato
Continuiamo con :
00401B26 PUSH 3 00401B28 LEA EAX, DWORD PTR SS:[ESP+14] VIENE SALVATO IL 1° E 2° CARATTERE INSERITO IN EAX (03) 00401B2C PUSH 40A96E ; ASCII "423096" VIENE PUSHATA L’ULTIMA PARTE DEL CODICE DEL PRG 00401B31 PUSH EAX METTI NELLO STACK 00401B32 MOV DWORD PTR SS:[ESP+1C], EBP
AZZERA 00401B36 CALL ESI 00401B38 LEA ECX, DWORD PTR SS:[ESP+10] VENGONO CARICATI IN ECX L’11° E 12° CARATTERE NUMERICO DEL SERIAL DATO AL PRG (42) 00401B3C PUSH ECX E VIENE PUSHATO 00401B3D CALL 0040253B CALL CHE TRASFORMA I CARATTERI PRESI IN ESADECIMALE (42 = HEX 2A) E LO METTE IN EAX ALL’USCITA 00401B42 CDQ 00401B43 AND EDX, 3 00401B46 ADD ESP, 4 00401B49 ADD EAX, EDX SOMMA EDX AD EAX ( 0 + 2A = 2A) 00401B4B MOVSX EDX, BYTE PTR DS:[40A92A] MUOVE IN EDX L’ULTIMA LETTERA DEL NOSTRO SERIALE (ASCII DI C = 43 HEX) 00401B52 SAR EAX, 2 EAX VIENE DIVISO PER 4 ( 2A / 4 = A) 00401B55 SUB EDX, 41 SOTTRAE AD EDX (IL NOSTRO 43 HEX RICORDARSI C ULTIMO NOSTRO CARATTERE INSERITO) 41 IL RISULTATO E’ = 02 00401B58 CMP EAX, EDX COMPARA IL NOSTRO ULTIMO CARATTERE (IN HEX) CON QUELLO CALCOLATO (A CON 02) 00401B5A JNZ SHORT 00401BC8 SE NON E’ UGUALE SALTA AL MESSAGGIO DI ERRORE |
Quindi se come abbiamo visto a EDX viene sottratto 41 noi dobbiamo fare in modo che la sottrazione di EDX con 41 dia come risultato A che è il nostro EAX ( quindi A+41 = 4B che è quello che noi dobbiamo avere in EDX e cioè al posto del nostro ultimo carattere inserito C)
Cosa è 4B in ASCII? Andiamo a vedere sulle nostre tabelle dei codici ASCII e vediamo che a 4B corrisponde la lettera K il nostro esatto ultimo carattere.
Reinseriamo il tutto e ripartiamo, il terzo step è superato.
Come potete vedere l’algoritmo di calcolo continua fino alla fine con le stesse modalità
00401B5C PUSH 3 00401B5E LEA EAX, DWORD PTR SS:[ESP+14] VIENE SALVATO IL 11° E 12° CARATTERE DEL PRG IN EAX (42) 00401B62 PUSH 40A970 ; ASCII "3096" VIENE PUSHATO L’ULTIMA PARTE DEL CODICE DEL PRG 00401B67 PUSH EAX INSERISCE (42) NELLO STACK 00401B68 MOV DWORD PTR SS:[ESP+1C], EBP AZZERA 00401B6C CALL ESI 00401B6E LEA ECX, DWORD PTR SS:[ESP+10] VIENE SALVATO IL 13° E 14° CARATTERE DEL PRG IN ECX (30) 00401B72 PUSH ECX E VIENE PUSHATO 00401B73 CALL 0040253B CALL CHE TRASFORMA I CARATTERI PRESI IN ESADECIMALE (30 = HEX 1E) E LO METTE IN EAX ALL’USCITA 00401B78 CDQ 00401B79 AND EDX, 3 00401B7C ADD ESP, 4 00401B7F ADD EAX, EDX SOMMA EDX AD EAX ( 0 + 1E = 1E) 00401B81 MOVSX EDX, BYTE PTR DS:[40A929] MUOVE IN EDX SERIALE (ASCII B = HEX 42) 00401B88 SAR EAX, 2 DIVIDI EAX PER 4 (1E / 4 = 7) 0401B8B SUB EDX, 41 SOTTRAI AD EDX (IL NOSTRO B = 42 HEX) 41 IL RISULTATO E’ 42 – 41 = 01 00401B8E CMP EAX, EDX COMPARA IL NOSTRO ULTIMO CARATTERE (IN HEX) CON QUELLO CALCOLATO (07 CON 01) 00401B90 JNZ SHORT 00401BC8 SE NON E’ UGUALE SALTA AL MESSAGGIO DI ERRORE |
Proprio identico al listato precedente quindi stessa procedura di calcolo EAX + 41 (7 + 41 = 48) che in ASCII corrisponde a H che andiamo ad inserire al posto della nostra penultima lettera inserita B.
E infine l’ultimo step. E’ lo stesso codice i sopra quindi non lo commento nemmeno.
00401B92 PUSH 3 00401B94 LEA EAX, DWORD PTR SS:[ESP+14] 00401B98 PUSH 40A972 ; ASCII "96" 00401B9D PUSH EAX 00401B9E MOV DWORD PTR SS:[ESP+1C], EBP 00401BA2 CALL ESI 00401BA4 LEA ECX, DWORD PTR SS:[ESP+10] 00401BA8 PUSH ECX 00401BA9 CALL 0040253B 00401BAE CDQ 00401BAF AND EDX, 3 00401BB2 ADD ESP, 4 00401BB5 ADD EAX, EDX 00401BB7 MOVSX EDX, BYTE PTR DS:[40A928] 00401BBE SAR EAX, 2 00401BC1 SUB EDX, 41 00401BC4 CMP EAX, EDX 00401BC6 JE SHORT 00401BD8 |
Stesso discorso di sopra EAX+41 (18+41 = 59) che in ASCII corrisponde a Y.
Abbiamo così trovato il nostro seriale: 0352YHK
A proposito se inserite nel nome e nel cognome meno di tre caratteri il programma vi da il messaggio di errore quindi attenzione.
A questo punto e d’obbligo anche il Keygen che vi allego sotto in Visual Basic
Inserite in un Form , 4 TextBox (una per il nome, una per il cognome , una per il seriale dato dal prg e una per il seriale calcolato)
Inserire 4 Label per indicare quanto sopra (Inserire il nome...etc)
Inserire 2 CommandButton (Command1 per calcolare e Command2 per azzerare l TextBox)
Infine inserite il codice sotto.
Option Explicit
Dim a, b, c, d, e, f As Integer
Dim Mystr1, Mystr2, Mystr3 As String
Dim My1, My2, My3, My4, My5, My6, My7, My8, My9 As Integer
Private Sub Command1_Click()
If ctrlInput = True Then
My2 = Val(Mid$(Text1, 1, 2))
My3 = Val(Mid$(Text1, 3, 2))
My1 = My2 - My3
If My1 < 10 Then
Mystr1 = "0" + Trim$(Str$(My1))
Else
Mystr1 = Trim$(Str$(My1))
End If
My4 = Asc(Mid$(Text1, 9, 1))
My5 = Asc(Mid$(Text1, 8, 1))
My6 = (My5 - My4)
My7 = Asc(Mid$(Text1, 7, 1))
My8 = Asc(Mid$(Text1, 6, 1))
My9 = ((My6 - My7) + My8)
If My9 < 10 Then
Mystr2 = "0" + Trim$(Str$(My9))
Else
Mystr2 = Trim$(Str$(My9))
End If
a = Val(Mid$(Text1, 11, 2))
b = Int(a / 4) + 65
c = Val(Mid$(Text1, 13, 2))
d = Int(c / 4) + 65
e = Val(Mid$(Text1, 15, 2))
f = Int(e / 4) + 65
Text2 = Mystr2 + Mystr1 + Chr$(Trim$(Str$(f))) + Chr$(Trim$(Str$(d))) + Chr$(Trim$(Str$(b)))
End If
End Sub
Private Function ctrlInput() As Boolean
If Len(Text1) = 0 Then
MsgBox "ATTENZIONE!!! Devi inserire il codice generato dal programma denominato Your Serial Number", vbExclamation, ""
Text1.SetFocus
Exit Function
End If
If Len(Text3) < 3 Then
MsgBox "Il campo primo nome deve contenere almeno tre (3) caratteri", vbExclamation, ""
Text3.SetFocus
Exit Function
End If
If Len(Text4) < 3 Then
MsgBox "Il campo secondo nome deve contenere almeno tre (3) caratteri", vbExclamation, ""
Text4.SetFocus
Exit Function
End If
ctrlInput = True
End Function
Private Sub Command2_Click()
Text2 = ""
Text3 = ""
Text4 = ""
Text1 = ""
End Sub
Private Sub Form_Activate()
Me.Left = (Screen.Width - Me.Width) / 2
Me.Top = (Screen.Height - Me.Height) / 2
Text1.SetFocus
End Sub
DesTroYer
Note finali |
Ringrazio Quequero per la sua disponibilità e per la pazienza che dimostra nel pubblicare questi tutorial raccapriccianti.
Disclaimer |
Vorrei ricordare che il software va comprato e non rubato, dovete registrare il vostro prodotto dopo il periodo di valutazione. Non mi ritengo responsabile per eventuali danni causati al vostro computer determinati dall'uso improprio di questo tutorial. Questo documento è stato scritto per invogliare il consumatore a registrare legalmente i propri programmi, e non a fargli fare uso dei tantissimi file crack presenti in rete, infatti tale documento aiuta a comprendere lo sforzo che ogni sviluppatore ha dovuto portare avanti per fornire ai rispettivi consumatori i migliori prodotti possibili.
Reversiamo al solo scopo informativo e per migliorare la nostra conoscenza del linguaggio Assembly.