Opfer : Cruehead's CrackMe v1.0
Woher : http://neuromancerz.cjb.net/
Author: Terminal Cilla


			Hiya Leute,
ich mchte Euch heute einen Einblick in die Funktionsweise
der Registrierungsroutine von Cruehead's Crackme v1.0 geben.
Falls ich etwas Falsches erzhlen sollte, dann informiert
mich bitte - denn ich bin auch nur ein newbie...
...danke.
 
Wir starten das Crackme und setzen einen
Breakpoint auf 'DialogBoxParamA', sicherlich knnten
wir auch andere bpx s benutzen, aber dieser bietet
sich in unserem Falle geradezu an.
Wenn wir nun auf 'Register' gehen, landen wir prompt in
SoftIce, da wir aber hier noch nicht halten wollen, drcken
wir F12 und sehen den Eingabe-Dialog.
Wir geben irgendetwas ein und drcken OK und sofort
sind wir bei SoftIce. Diesmal jedoch sind wir genau im Herzen
der Registrierungsroutine.

Wir landen hier: 
-----------------------------------------------------------------------
:00401223 83F800                  cmp eax, 00000000
:00401226 74BE                    je 004011E6
	Ist ein Name eingegeben worden? 
	Wenn nicht, dann springe gleich zur Fehlermeldung, 
	ansonsten fahre fort.
	Wenn ein Name angegeben wurde, dann ist EAX=1, anderfalls
	ist EAX=0.
	'Je' entspricht 'Jz'(JumpIfZero), d.h. wenn EAX=0 ist,
	wird gesprungen. 

:00401228 688E214000              push 0040218E
	Unser Name wird auf dem Stack abgelegt.

:0040122D E84C010000              call 0040137E (1.call)
	In diesem call wird unser Name be/verarbeitet.

:00401232 50                      push eax
	Das Ergebnis der Verarbeitung wird wieder im Stack abgelegt.

:00401233 687E214000              push 0040217E
	Unsere Serial wird auf dem Stack abgelegt.

:00401238 E89B010000              call 004013D8 (2.call)
	Hier wird unsere Serial be/verarbeitet.

:0040123D 83C404                  add esp, 00000004
	Nicht so wichtig;)

:00401240 58                      pop eax
	Lade unseren modifizierten Namen aus dem Stack.

:00401241 3BC3                    cmp eax, ebx
	Vergleiche Resultat aus dem 1.call und den 2.call.
	Hier werden EAX und EBX subtrahiert...

:00401243 7407                    je 0040124C
	...und wenn dann 0 rauskommt, springen wir zur 
	Glckwunschmeldung ('je'='jz').
	Wenn jedoch etwas anderes im Ergebnis steht, dann
	gelangen wir zur Fehlermeldung.
	Folglich mssen EAX und EBX den selben Wert haben,
	damit beim Subtrahieren der beiden 0 im Ergebnis steht.

:00401245 E818010000              call 00401362
	Der call enthlt eine Fehlermeldung.
----------------------------------------------------------------------------

OK, lasst uns mal den 1.call genauer anschauen:
----------------------------------------------------------------------------
* Referenced by a CALL at Address:
:0040122D   

:0040137E 8B742404                mov esi, dword ptr [esp+04]
:00401382 56                      push esi
	Speichere unseren Namen in ESI.

:00401383 8A06                    mov al, byte ptr [esi] ->Schleifenanfang
	ESI bezeichnet die gegenwrtige Stelle in der Zeichenkette (Name).
	Da ESI=0 ist, wird der erste Buchstabe in AL gespeichert.
	Wenn ESI um eins erhht wird, wre es der zweite Buchstabe.

:00401385 84C0                    test al, al
:00401387 7413                    je 0040139C
	Wenn AL=0, d.h wenn der letzte Buchstabe erreicht wurde, 
	dann springe weg. Ansonsten mach' weiter...

:00401389 3C41                    cmp al, 41
:0040138B 721F                    jb 004013AC
	Wenn eins unser Zeichen im Namen unter 41h ist, dann gehe zur
	Fehlermeldung.
	41 ist in Hex, umgewandelt whre es 65 und das entspricht
	dem 'A'. Wenn nun ein Zeichen in userem namen vorkommt, das
	in der ASCII - Tabelle unter dem 'A' steht, dann gibt's die
	Fehlermeldung. Also verzichten wir auf Zahlen usw.

:0040138D 3C5A                    cmp al, 5A
:0040138F 7303                    jnb 00401394
	Wenn wir Zeichen benutzen deren ASCII - Wert grer als 90 ist,
	dann wird eine Prozedur aufgerufen, die den gegenwrtigen ASCII -
	Wert mit 32 subtrahiert. Aus kleinen Buchstaben werden so groe.

:00401391 46                      inc esi
	Erhhe ESI um eins.

:00401392 EBEF                    jmp 00401383
	Gehe zum Schleifenanfang

---------------|---
Bis hierher wird also nur getestet, was fr Zeichen wir eingegenben
haben und eventuell werden diese noch konvertiert. Aber wir
wissen auch welche Zeichen wir uns gleich sparen knnen.
Jetzt schauen wir uns an, wie's weiter geht, wenn die
Schleife durchlaufen ist.(siehe oben :00401387).
---------------|---
* Referenced by a (U)nconditional or (C)onditional Jump at Address:
:00401387(C)

:0040139C 5E                      pop esi
	Lade unsere Namen aus dem Stack.

:0040139D E820000000              call 004013C2
	Diesen call schauen wir uns mal genauer an:
	
	--------------------
	* Referenced by a CALL at Address:
	:0040139D   

	:004013C2 33FF                    xor edi, edi
	:004013C4 33DB                    xor ebx, ebx
		EDI=0 und EBX=0.

	:004013C6 8A1E                    mov bl, byte ptr [esi] 
	->Schleifenanfang.
		Wie oben. BL hlt den jeweiligen Buchstaben.

	:004013C8 84DB                    test bl, bl
	:004013CA 7405                    je 004013D1
		Sind wir am Ende der Zeichenkette?
		Wenn ja, dann kehren wir hier zum call-Aufruf zurck.
		Wenn nicht...
	:004013CC 03FB                    add edi, ebx
		Addiere den ASCII - Wert des derzeitigen Buchstabens mit
		dem Inhalt von EDI. Da EDI beim dem ersten Aufruf 0 ist, 
		wird mit 0 addiert.
	:004013CE 46                      inc esi
		Erhhe ESI ums eins und gehe zum schleifenanfang.
	:004013CF EBF5                    jmp 004013C6
	--------------------

Zurck in unsere eigentlichen Routine.
--------------------
:004013A2 81F778560000            xor edi, 00005678
		Xor das Ergebnis des calls (:0040139D) mit 5678h.
:004013A8 8BC7                    mov eax, edi
	Speicher das Ergebnis in EAX.
:004013AA EB15                    jmp 004013C1
----------------------------------------------------------------------------

Puhh, das war jetzt etwas wild, oder?
Ist eigentlich auch wurscht, da wir ja bei :00401232 sowieso sehen,
was EAX enthlt.
Schauen wir uns nun den 2.call an:
----------------------------------------------------------------------------
 Referenced by a CALL at Address:
:00401238   

:004013D8 33C0                    xor eax, eax
:004013DA 33FF                    xor edi, edi
:004013DC 33DB                    xor ebx, ebx
	Lsche EAX, EDI und EBX.

:004013DE 8B742404                mov esi, dword ptr [esp+04]
	Serial nach ESI.

:004013E2 B00A                    mov al, 0A -> Schleifenanfang
	AL=10.

:004013E4 8A1E                    mov bl, byte ptr [esi] ->kennt Ihr ja;)
:004013E6 84DB                    test bl, bl
:004013E8 740B                    je 004013F5 ->Fertig? Dann weg. -------
:004013EA 80EB30                  sub bl, 30				|
	Subtrahiere 48 vom gegenwrtigen ASCII - Wert.			|
									|
:004013ED 0FAFF8                  imul edi, eax				|
	EDI=EDI*EAX							|
									|
:004013F0 03FB                    add edi, ebx				|
	EDI=EDI+EBX							|
									|
:004013F2 46                      inc esi				|
:004013F3 EBED                    jmp 004013E2 ->kennt Ihr auch		|
									|
:004013F5 81F734120000            xor edi, 00001234----------------------
	Xor Inhalt von EDI mit 1234h.

:004013FB 8BDF                    mov ebx, edi
EDI nach EBX.
:004013FD C3                      ret
----------------------------------------------------------------------------
Eigentlich macht diese ganze Routine nichts weiter, als das, was Euer
Taschenrechner macht, wenn Ihr eine Zahl nach Hex konvertiert.
Blo das diese hierbei noch mit 1234h ge-xor-ed wird.
Beispiel:
12345 ->Gebt Ihr ein...
3039  ->das Programm rechnet nach Hex um...
220D  ->Ergebnis nach dem xor.
----------------------------------------------------------------------------

So, das waren jetzt 'n ganze Menge an Infos.
Falls Ihr noch nicht abgeschaltet habt vor Langerweile oder
gerade wieder aufgewacht seit, knnen wir weitermachen.
Wie schaffen wir es, das bei :00401241 EAX und EBX gleich sind?
Lasst uns mal erinnern, wir mssen eine Serial eingeben, die
ge-xor-ed mit 1234h das Gleiche ergibt wie der Inhalt von EAX (Name) nach 
dem 1.call.
Was ist das Gegenteil von xor? Wieder xor!
Also wie wre es, wenn wir EAX mit 1234h xor-en und die erhaltene
Zahl als dezimal eingeben wrden?
Richtig, unser Opfer wrde unsere neue Serial in Hex umwandeln
und mit 1234h xor-en und somit auf den Inhalt von EAX kommen.
Testen wir das...

Ich nehme Terminal_Cilla als Name und irgendeine dumme Serial.
Nach unserem 1.call bei :00401232 schauen wir uns EAX an.
Bei mir enthlt es: 54A6.
Jetzt xor-en wir das ganze mit 1243h (Taschenrechner!) und wandeln
nach dezimal um.
54a6 xor 1234 = 4692 (<->18066!)
Wir merken uns die Dezimalzahl. Noch mal berlegen...
wenn das Programm nun die Dezimalzahl in Hex umwandelt
(18066->4692) und dann mit 1234h xor-ed, dann kommen wir
worauf? (4692 xor 1234 =54A6)!!! Dada! Ja, genau auf
den Wert von EAX - unser modifizierter Name.
Somit hat EBX den gleichen Wert wie EAX und
wenn die beiden nun verglichen werden, dann
erhalten wir 0 und der je (jz) bring uns zur Glckwunschmeldung!

Wenn Ihr wollt knnt Ihr nun einen Keygen basteln - 
ich will's nicht mehr, deshalb bleibts bei den paar Zeilen;)
----------------------------------------------------------------------------
			Peace&Respect to: 
	duelist, Torn@do, TheAntiXryst, rubor und Sanhedrin.

Spezielle Gre an: Patrick, Nicole, Manja, Franzi & Kati!


(c) Terminal Cilla (Mai 1999) [http://beam.to/CUG]
    bombasticx@gmx.net



 



