Prueba de seguridad para explorar el juego de Windows Buscaminas

Autor:  Wan Yuxin de Jingdong Industry

Creo que muchas personas han jugado juegos de buscaminas desde que eran jóvenes. En esa época en que no había muchos juegos de computadora, el buscaminas se convirtió en uno de los juegos más populares. Más tarde, también tuve la necesidad de hacerlo una vez. A través de la depuración dinámica, la ingeniería inversa y C para escribir una herramienta auxiliar de buscaminas para mejorar las habilidades de ingeniería inversa y codificación.

Depuración dinámica (análisis)

Primero, realice una depuración dinámica (análisis) del programa buscaminas:

Abra OD ( herramienta ollydebug ), arrastre y suelte el buscaminas en OD , F9 para ejecutar; ctrl+G para ingresar la expresión a seguir, ingrese rand , haga clic en [OK] para saltar a la llamada de función, F2 para establecer un punto de interrupción, este El el segundo es encontrar un gran avance a través de la función API rand . Haga clic en cualquier posición en el campo minado de la ventana del buscaminas (donde aparece 2 en la imagen ), y luego haga clic en Restaurar (botón [Cara sonriente] - ), como se muestra en la siguiente figura:



En este momento, el OD se romperá en el punto de ruptura en el rand recién establecido , como se muestra en la siguiente figura:



 

Al encontrar la función aleatoria rand , la siguiente pila retrocede y regresa a la función de nivel superior para encontrar los parámetros de empujar (empujar en la pila), es decir, la función de generación aleatoria ( rand ) es una altura generada aleatoriamente, ancho y trueno. Haga clic en K (pila de llamadas) para abrir la ventana de la pila de llamadas K , vea la información de la ventana de la pila, encuentre la dirección de retorno, haga doble clic en la dirección de retorno en la ventana de la pila de llamadas K y regrese a la capa anterior. retroceder la pila. Observe atentamente la información de la pila 010036D2 (dirección de retorno) en la siguiente figura .







F8 de un solo paso , observe los cambios en el registro, la ventana de datos y la ventana de pila, dword ptr ss:[esp+0x4] o dword ptr ds:[XXX] valor de seguimiento de la ventana de datos ( 000DFC44 el valor es 09 ), como se muestra a continuación:

Después de volver a la función de nivel superior, analice las instrucciones internas y conozca el ancho ( 09 ) generado por rand aleatorio en este momento , como se muestra en la figura a continuación, preste atención a la dirección 010036C7 .

Primero, analice eax a partir del resultado devuelto por esta función . Después de un solo paso, puede ver que se inserta un número 09 en la pila (dirección 010036D2 ) , como se muestra en la siguiente figura:



A través del análisis anterior, básicamente se puede adivinar que la generación de rand de función aleatoria circundante es alta, número de trueno. Puede intentar cambiar la configuración de búsqueda de minas (campos de minas personalizados), como se muestra en la figura a continuación, para ubicar con precisión la función rand y pasar parámetros, haga clic en [Aceptar] y luego haga clic en el botón [Restaurar (cara sonriente - )].



 

Observe el OD , como se muestra en la siguiente figura:



 

Se encuentra que empujar 0C ( el valor de 000DFC84 es 0C ), se puede determinar que el empuje 0C de esta función rand es la altura del campo minado. Al mismo tiempo, puede ver claramente un gráfico de campo minado aproximado en el área de memoria. A través del método anterior, puede adivinar aproximadamente que 0x80 es un campo minado. O analice junto con IDA , a través del análisis estático, puede ver la lógica del programa de manera más intuitiva. Obtenga los siguientes datos: dirección base, número de mina y otra información, como se muestra en la siguiente figura:







 

El código anterior probablemente significa que las variables de ancho global 0x09 , alto 0x0C y número de trueno 0x0A se establecen primero , y el ancho y el alto se generan aleatoriamente al juzgar dos capas de bucles. Obtenga la dirección base del mapa: 0x01005340 . Al analizar la figura a continuación, sabemos que ninguna mina es 0x0F , la mía es 0x8F y la pared es 0x10 .







 

A través de las direcciones de ancho y alto, se imprime el área de barrido de minas y el número de minas, y las paredes laterales y las minas se pueden distinguir de manera más intuitiva.

A continuación, comencemos a descubrir cómo marcar a Lei. Suponiendo que la función GetDC se ve en WinProc (retrocediendo a través de la pila hasta la función de devolución de llamada del mensaje) , se supone aproximadamente que se usará Bitblt . En OD , ingrese la expresión para ser seguido por ctrl+g , e ingrese " BitBlt ", presione F2 para establecer un punto de interrupción, haga clic en cualquier posición en el área de búsqueda de minas y el OD se interrumpirá en la posición de BitBlt .

También hay una función BitBlt en BitBlt.El juicio preliminar es que utiliza doble almacenamiento en búfer para dibujar.

BitBlt(hDestDC,// Destino DC XDest, // Coordenada x de destino YDest, // Coordenada y de destino 10, // 10, // Alto y ancho del área de redibujado hSrcDC, // DC de origen 0, 0, SRCCOPY); / / Especifique el método de operación para calcular las coordenadas de la mina (haga clic en el primer cuadrado de barrido de minas para ver las coordenadas), debe prestar atención a la pared lateral, como se muestra a continuación:







 

Reste el valor de las paredes laterales:

-0x04=0x0C(12)-0x10(16)

0x27=0x37(55)-0x10(16)

Obtenga la fórmula de coordenadas: x ( XDest:12 ) =1*0x10(16)-0x04(4) , y ( YDest:55 ) =1*0x10(16)+0x27(39).

escritura de código

A través del análisis aproximado anterior, el código se puede escribir,





 





 

logro





 

Ingrese 3 ubicaciones de minas terrestres para obtener minas terrestres ( 10 paredes, mina terrestre 8F , 0F sin mina)





 

Ingrese 2 para borrar automáticamente las minas, marcar las minas y abrir el mapa





 

A través de este pequeño proyecto, en primer lugar, se ha fortalecido una especie de pensamiento inverso sobre el software, como: al ver este tipo de panel, probablemente supuse que está implementado con una matriz, y en segundo lugar, el diseño del mío es aleatorio. generado, y luego a través de la depuración dinámica, podemos entender El método de implementación (una idea de implementación del desarrollador), puede encontrar la dirección base clave, varios estados (sin trueno, trueno, pared), la última etapa de codificación puede entender el funcionamiento de la memoria, varias API importantes, FindWindow para obtener el identificador, OpenProcess abre el identificador, ReadProcessMemory lee la información de la memoria, modo de mensaje asíncrono PostMessage , CloseHandle cierra el identificador. Parte del análisis es incorrecto o no está en su lugar, por favor busque ladrillos. Más al revés, analizar el código es muy útil, no solo puede ampliar su pensamiento y nivel de programación y prueba, sino también descubrir, desarrollar y explotar lagunas en el programa o parchear el programa, etc. Espero que mis amigos trabajen duro y se animen unos a otros en este largo y arduo viaje.

{{o.nombre}}
{{m.nombre}}

Supongo que te gusta

Origin my.oschina.net/u/4090830/blog/8590989
Recomendado
Clasificación