| ESTUDIO COLECTIVO DE DESPROTECCIONES Última Actualizacion: 25/10/2001 |
Programa | Crackear archivos empaquetados III. Usando memoria virtual. Star Strider v1.5 | W95 / W98 / NT
Descripción | unknown
Tipo | unknown
Tipo de Tutorial | [X]Original, []Adaptación, []Aplicación, []Traducción
Url | unknown
Protección | Serial
Dificultad | 1) Principiante, 2) Amateur, 3) Aficionado, 4) Profesional, 5) Especialista
Herramientas | Snippet Creator v1.5 HexWorkShop SoftIce TASM v5.0
Objetivo | Simular estar registrados.
Cracker | n u M I T_ o r
Fecha | Enero 2000
INTRODUCCION
Bien amigos, seguro que alguna vez han encontrado programas fácil de desproteger pero que presentan el problema de estar empacados y no es tan fácil parcharlos. Algunos crackers han superado este obstáculo empleando parcheadores de procesos (process partchers). Recientemente, y podemos constatarlo en los fabulosos tutoriale de R!SC, otros crackers detectan con un depurador -debugger- como Soft Ice los puntos donde colocar en archivo ejecutable los parches y en un breve análisis del ejecutable mismo ubica dónde insertar un recorte -snippet- que parche el programa cuando se despliega en memoria para su ejecución. A veces esto es relativamente sencillo, pero otras veces no tanto. Yo he implementado el uso de DLLs cuando el recorte es muy grande [ver CRACKEAR ARCHIVOS PE EMPAQUETADOS ( I I )] y el tamaño es un parámetro crítico. Ahora implementaré otro método para esto que me ha parecido más sencillo y mejor porque no requiere archivos adicionales: aprovechar las APIs del manejo de memoria virtual de Windows. ¿Cuándo usar este método? Cuando el espacio donde se ubica el recorte es limpiado y barrido por el programa en el momente que el archivo ejecutable es desempacado y no queremos usar una DLL para evitar esto. Esta técnica consiste en escribir el recorte de código y moverlo a un lugar seguro en la misma memoria del proceso, pero lejos del área de despliegue del ejecutable. De esta manera cuando se despliegue el programa no podrá alcanzar el recorte y destruirlo. Entonces el programa pasará el control al recorte en memoria para que el recorte de código parche el programa y lo desprotega (si éste es nuestro objetivo).
AL ATAQUE
Si cargamos el archivo StarStrider.exe con SoftIce e intetamos desplegar su contenido, no se disparará la ventana del depurador porque el programa está empaquetado y se han cambiado los atributos de las secciones. A esta altura ya deberíamos tener una idea de cómo desplegar el programa de un archivo empacado en Soft Ice. Abrimos el archivo con un editor de archivos PE (ProcDump o SnippetCreator) y cambiamos las características de la sección de código. Con SnippetCreator procedemos así: Creamos en SnippetCreator un nuevo proyecto (File/New Project) y llamémosle SS, cuyo target sería StarStrider.exe. Recabamos información sobre el encabezado del archivo (PE Info\View PE Header): Address Entry Point: 00 06 E0 00 h Ahora cambiamos las características de la sección de código (por lo general .text o .code). Ejecutamos PE Info\View Section Info. Vemos que el punto de entrada coincide con la dirección de inicio de la sección .aspack. Anotemos de una vez los siguientes valores de .aspack: V. Offset: 0006E000h Raw Offset: 00025400h Así que hacemos click con el botón derecho del ratón sobre .text (la sección de código) y elegimos Edit Section en el menú emergente; pulsamos el botón "..." de "Characteristics", elegimos IMAGE_SCN_CNT_CODE y IMAGE_SCN_CNT_EXECUTE y pulsamos el botón "Save". Ahora en en el campo "Characteristics" aparece E0 00 00 60h. Después de realizar esta operación con StartStrider.exe, carguémoslo con el "loader" de SoftIce y empleando F10, F9 y F5 estratégicamente busquemos el final del la rutina que desempaca el archivo: 0157:0046E5B1 50 PUSH EAX 0157:0046E5B2 0385A8304400 ADD EAX,[EBP+004430A8] 0157:0046E5B8 5B POP EBX 0157:0046E5B9 0BDB OR EBX,EBX 0157:0046E5BB 8985E12E4400 MOV [EBP+00442EE1],EAX 0157:0046E5C1 61 POPAD 0157:0046E5C2 7508 JNZ 0046E5CC 0157:0046E5CC 68305E4200 PUSH 00425E30 0157:0046E5D1 C3 RET Vamos a necesitar un espacio de seis bytes para la nueva instrucción, así que escogemos: 0157:0046E5BB 8985E12E4400 MOV [EBP+00442EE1],EAX Como antes, llamamos a esta dirección RVA1: es la dirección que entrega el control a nuestro recorte parchador. Como en otros casos que he analizado, esta instrucción también está empaquetada, así que para parcharla y reescribir en ella las instrucciones que entregan el control al recorte tenemos que esperar hasta que la instrucción misma sea desempacada porque si no, cuando la instrucción se despkliegue corroerá nuestro parche. Esto nos obliga a encontrar un punto anterior para dar el controla nuestro de código. Para esto ejecutamos en SoftIce el comando: D RVA1 = D 0046E5BB. En la ventana de datos podemos ir revisando hasta que en ella aparezca el código octal correspondiente a las instrucciones que queremos localizar. Cargamos StarStrider.exe con el "loader" de SoftIce, ejecutamos el comando D 0046E5BB y vamos trazando el programa con la tecla F10 hasta ver en la ventana de datos: 0030:0046E5BB 2EE18589 75610044 00 Es la representación en octal en reverso y ordenada en valores dword de: 8985E12E4400 MOV [EBP+00442EE1],EAX La instrucción que buscamos se despliega cuando se ejecuta la instrucción 0157:0046E0E7: 0157:0046E0E7 F3A4 REPZ MOVSB ; <- 0157:0046E0E9 8B8541294400 MOV EAX,[EBP+00442941] ; <- VA0 0157:0046E0EF 6800800000 PUSH 00008000 0157:0046E0F4 6A00 PUSH 00 0157:0046E0F6 50 PUSH EAX 0157:0046E0F7 FF9549294400 CALL [EBP+00442949] 0157:0046E0FD 8D851D2C4400 LEA EAX,[EBP+00442C1D] 0157:0046E103 50 PUSH EAX 0157:0046E104 C3 RET Así que podemos elegir la instrucción 0046E0E9, una instrucción de seis bytes y que se realiza cuando la instrucción VA1 ya está desplegada. Llamamos a esta instrucción VA0. Ahora tenemos que localizar un espacio para nuestro recorte de código. Podemos hacer esto con el editor hexadecimal y sin mucho tecnisismo. Abrimos StarStrider.exe con HexWorkshop y buscamos "manualmente" un espacio con gran cantidad de ceros. Hay varios, pero elegimos el espacio que comienza en el desplazamiento del archivo 00 01 DC 00 h. ¿Por qué? por intuición: a la vista parece suficiente. Para realizar nuestro trabajo tenemos que convertir el desplazamiento en el archivo a dirección virtual. Para eso aplicamos la siguiente fórmula: VA del recorte = (Desplazamiento del recorte - RawOffset de la Sección) + (ImageBase + VirtualOffset de la sección) Tenemos que ubicar en qué sección está el espacio para el recorte y especificar dónde comienza esa sección. Vemos que el recorte está entre, es decir, en la sección .rsrc, que inicia en la dirección virtual (VA) 00 04 00 00 h y cuyo desplazamiento en el archivo es 01 DC 00 h . Aplicando la fórmula tenemos: (00025260h - 0001DC00h) + (00400000h + 00040000h) = 00447660h Sólo nos queda ubicar las instrucciones que necesitamos cambiar para que el programa tenga el comportamiento de un programa registrado. Como supongo que el lector de este escrito ya debe tener cieta destreza ubicando los puntos frágiles de un programa, no explicaré como encontrarlo. Además ese no es el objeto de este escrito sino el aprender una estrategia para parchar archivos empaquetados. Así que de una vez indico que la instrucción a cambiar es: 0157:0042FBA3 51 PUSH ECX 0157:0042FBA4 52 PUSH EDX 0157:0042FBA5 E8D6000000 CALL 0042FC80 0157:0042FBAA 85C0 TEST EAX,EAX 0157:0042FBAC 7540 JNZ 0042FBEE 0157:0042FBEE BB88080000 MOV EBX,00000888 0157:0042FBF3 8BC3 MOV EAX,EBX 0157:0042FBF5 5B POP EBX 0157:0042FBF6 5E POP ESI 0157:0042FBF7 81C4D0000000 ADD ESP,000000D0 0157:0042FBFD C21400 RET 0014 Es muy simple lo que tenemos que hacer. Reemplazar la instrucción 0157:0042FBAA 85C0 TEST EAX,EAX por: 0157:0042FBAA EB2B JMP 0042FBD7 Con esta instrucción saltamos todas las pruebas que comprueban si el programa ha sido registrado hasta la dirección 0042FBD7, que es la dirección a donde debería llegar el programa si estuviera registrado. E l R e c o r t e Ahora lo decisivo: escribir el recorte. Corremos Snippet Creator y abrimos el proyecto SS que creamos al principio. Establecemos las opciones del proyecto: He descubierto que (aunque no sé porqué motivo) algunas acciones hechas por Snippet Creator sobre archivo PE empaquetados deterioran el archivo. Así que muchas opciones de Snippet Creator que podrían ahorrarnos trabajo no se pueden emplar cuando injertamos código nuevo en ejecutables. Así que nos conformaremos con las siguientes opciones (ejecutamos Action\Project Options para desplegar el diálogo Project Options): Snippet VA: 477660 Patch Options: Patch Into Existing Section Address to Redirect Control to the Snippet: No Redirection Return Control To Program: Don't Return Control To Program Otras opciones que no hemos podico elegir tendremos que realizarlas nosotros mismos "manualmente". No es difícil hacerlo. Este es el recorte de código: ; ------------------------------------------------------------------------------------------------ extrn LoadLibraryA:near extrn GetProcAddress:near jmp numit1 l1 db 'kernel32.dll',0 f1 db 'VirtualAlloc',0 OldInstruction db 08Bh,085h,041h,029h,044h,000h NewInstruction db 068h,000h,000h,000h,000h,0C3h numit1: ; Restaurar antigua instrucción pushad mov esi,offset OldInstruction mov edi,46E0E9h mov ecx,6 rep movsb ; Obtiene la dirección de la función VirtualAlloc en la memoria del proceso push offset l1 call [LoadLibraryA] push offset f1 push eax call [GetProcAddress] ; Reservar espacio en memoria para el recorte mov esi,(final - init) push esi call eax,0,esi,1000h,40h ; Mover el código a la memoria mov edi,eax lea esi,init pop ecx rep movsb ; Escribir el salto al código en memoria mov edi,46E5BBh lea esi,NewInstruction mov dword ptr [esi+1],eax mov ecx,6 rep movsb ; Regresar popad push 46E0E9h ret init: pushad ; Restaurar instrucción original mov edi,46E5BBh mov dword ptr [edi],02EE18589h mov word ptr [edi+4],0044h ; Escribir el parche mov edi,42FBAAh mov word ptr [edi],2BEBh ; Regresar popad push 46E5BBh ret final: ; ------------------------------------------------------------------------------------------------ Puedes ver que este código, cuando toma el control por vez primera: · Restaura la instrucción original en VA0 = 46E0E9h · Obtiene la dirección de las funciones VirtualAlloc y VirtualFree. · Compromete memoria física con la función VirtualAlloc. · Mueve el recorte de código parchador a la región de memoria comprometida. · Cambia la instrucción en la dirección 46E5BBh para que en una segunda ocasión devuelva una váz más el control al recorte, ahora en el área de memoria comprometida. · Devuelve el control al programa en la dirección VA0. Cuando el programa vuelve a tomar el control y alcanza la dirección VA, devuelve por segunda vez el control al recorte, ahora ubicado en una región de memoria que previamente comprometimos para él. En esta segunda ocasión el código de recorte: · Restaura la instrucción original en VA1 = 46E5BBh · Parcha el proceso en VA2 = 42FBAAh · Retorna el control al programa. La parte interesante del recorte es: ; -------------------------------------------------------------------------------------------------- ; Obtiene la dirección de la función VirtualAlloc en la memoria del proceso push offset l1 call [LoadLibraryA] push offset f1 push eax call [GetProcAddress] ; Devuelve en eax la dirección de VirtualAlloc, en este caso. ; Reservar espacio en memoria para el recorte mov esi,(final - init) ; Tamaño del recorte push esi call eax,0,esi,1000h,40h . ; Mover el código a la memoria mov edi,eax ; Dirección dónde se halla el recorte lea esi,init ; Dirección del recorte en el código fuente pop ecx ; Tamaño del recorte rep movsb ; Mover el recorte ; -------------------------------------------------------------------------------------------------- Este código es lo que permite no tener que usar DLLs ni loaders, y evita tener que aumentar el tamaño del ejecutable PE que estamos tratando. Ahora ensamblamos el recorte (click sobre el botón "Assemble"), exportamos el binario y lo llamamos SS.BIN P a t c h i n g Abrimos una vista de nuestro target y otra del binario SS.BIN que hemos exprotado. Marcamos con el ratón toda el área correspondiente al código de nuestro binario SS.BIN y lo copiamos (CTRL+C). Luego marcamos el área del ejecutable StarStrider.exe correspondiente al espacio donde insertaremos el recorte: desde 025260h hasta 025326h y pegamos el binario que copiamos antes (CTRL+V). Repito una vez más que esta es la operación más delicada del proceso: copiar un byte de más o de menos daña por completo el archivo empacado. Lo último que nos queda es escribir en el ejecutable StarStrider.exe la instrucción en VA0 = 46E0E9h que entregará por vez primera el control al recorte. Calculemos el desplazamiento: Desplazamiento en el Archivo = ( VA0 - VA de la sección ) + RawOffset de la Sección El salto está en la sección .aspack cuya (VA) es 46E000h y cuyo desplazamiento en el archivo es ( 46E0E9h - 46E000h ) + 00025400h = 254E9h Nos movemos ahora en el editor hexadecinal (HexWorkshop) hasta 254E9h (Edit\Goto) y escribimos: 68 60 76 44 00 C3 Es el código en octal que corresponde a las instrucciones 68 60 76 44 00 push 00447660 ; VA2 C3 ret Son las instrucciones que entregan por vez primera el control al recorte. Con esto el programa casi parecerá registrado. Sólo queda colocar nuestro nombre de usuario y la clave en la subclave correspondiente del registro de Windows. ¿Cómo encontramos esa subclave? Podemos trazarla con una trampa en Soft Ice sobre la función RegQueryValueExA o con un monitor de las llamadas al registro de Windows como Registry Monitor de Mark Rusinovich. Yo encontré que era: HKCU\Software\FMJ-Software\StarStrider\ Hay que crear una clave llamada "Username" cuyo dato sería una cadena con el nombre del usuario. P a r a T e r m i n a r Bueno. Con esto termino esta serie en tres partes sobre desprotecciones de archivos PE empaquetados. Yo encuentro este último procedimiento más conveniente que el implementado con las DLLs para crackear archivos empaquetados. Pero en algunos respectos prácticos el método de las DLLs podría resultar más atractivo. Gracias a Iczelion - Stone - _mammon, por sus extraordinarios conocimientos y herramientas. Trato de pagar la deuda con ellos compartiendo libremente lo que he aprendido y cada día descubro.
[ Entrada | Documentos Genéricos | WkT! Web Site ]
[ Todo el ECD | x Tipo de Protección | x Fecha de Publicación | x Orden Alfabético ]
(c) Whiskey Kon Tekila [WkT!] - The Original Spanish Reversers. Si necesitas contactar con nosotros , lee esto antes e infórmate de cómo puedes ayudarnos