miércoles, 8 de febrero de 2012

Introducción a la ingeniería inversa x86 (Parte III)

En la entrada anterior vimos algunos ejemplos de código en C y su equivalente en ensamblador. Hoy continuaremos con algunos ejemplos más que nos permitan entender más como funcionan los registros y ensamblador.

Pero antes de comenzar y ya que en el anterior post vimos un ejemplo de salto (JLE) debido a un bucle vamos a profundizar un poco más en el asunto.

Si recordáis la instrucción JLE (Jump if Less than or Equal) realizaba el salto a la dirección indicada si la condición se cumplía. ¿Pero como sabe si esta se cumple o no? Aquí es donde entra el registro de estado y sus FLAGS, el cual sirve para indicar el estado actual de la máquina y el resultado de algún procesamiento mediante bits de estado, entre los cuales podemos encontrar los siguientes:

  1. OF (overflow): Indica desbordamiento del bit de mayor orden después de una operación aritmética de números con signo (1=existe overflow; 0=no existe overflow).
  2. SF (Sign): Contiene el signo resultante de una operación aritmética (0=positivo; 1=negativo).
  3. PF (paridad): Indica si el número de bits 1, del byte menos significativos de una operación, es par (0=número de bits 1 es impar; 1=número de bits 1 es par).
  4. CF (Carry): Contiene el acarreo del bit de mayor orden después de una operación aritmética.
  5. ZF (Zero): Indica el resultado de una operación aritmética o de comparación (0=resultado diferente de cero; 1=resultado igual a cero).

Como ya habréis intuido, los flags ZF, SF y OF serán los más utilizados en comparadores y saltos. Retornamos al ejemplo del post anterior donde teníamos algo similar al siguiente código:

image

Teniendo en cuenta que se está ejecutando la instrucción JLE, nos interesa saber con que registros de estado trabaja la misma (http://faydoc.tripod.com/cpu/jle.htm).

0F 8E

JLE

Jump near if less or equal (ZF=1 or SF<>OF)

Como se ha podido observar, la instrucción JLE trabaja con los registros ZF, SF y OF, por lo que mientras la condición se cumpla nos encontraremos dentro del bucle. Para verlo todo más claro, vamos a ver la secuencia en ensamblador y como afecta al registro de estado.

image

Como veis, hasta que NO se ha cumplido la sentencia (ZF=1 o SF <> OF) no se ha salido del bucle. De este modo en la vuelta diez el bucle dejará de ejecutarse.

Una vez entendido como funcionan algunos de los registros de estado, continuamos con alguna de las equivalencias entre lenguaje C y ensamblador.

4 - Operaciones matemáticas

Vamos a ver como realiza ensamblador algunos cálculos matemáticos básicos.

image

Tal y como se puede observar en la captura anterior, se trata de un simple código que calcula la suma, resta, multiplicación y división de dos variables. Voy a dividir el código en cuatro partes para visualizarlo con más facilidad.

Empezamos con una simple suma:

image

Utilizando la instrucción LEA carga el contenido de EAX+EDX en EAX, por lo que ya tenemos nuestro resultado en un registro para posteriormente imprimirlo por pantalla.

En el siguiente código se encuentra la equivalencia a la resta.

image

En este caso se utiliza la instrucción SUB para restar el contenido de EAX a ECX, y almacenarlo nuevamente en ECX.

En el siguiente código se encuentra la equivalencia a la multiplicación.

image

Para realizar la multiplicación de dos variables, se utiliza la instrucción IMUL, el cual multiplica el primer valor por el segundo, almacenando el resultado de la operación en el primer valor.

En el siguiente código se encuentra la equivalencia a la división.

image

Para realizar la división de dos variables son necesarias dos instrucciones:

  1. CDQ se encarga de convertir el valor de 32 bits almacenado en EAX, en uno de 64 bits almacenado en EDX:EAX.
  2. IDIV se encarga de dividir el valor almacenado en EAX con el valor que se le pasa a la instrucción.

Después de conocer parte del registro de estado, como es utilizado para realizar bucles y algunas operaciones matemáticas básicas, doy por finalizado el post de hoy. Pronto volveré con algo más de esta serie de introducción a la ingeniería inversa :)

Un Saludo!!

4 comentarios:

  1. Excelentes artículos y menudo ritmo!

    ResponderEliminar
  2. Jajajjaj merci ;) Son las ganas del principio :P

    ResponderEliminar
  3. ¿Cuando reversing de código .net? :)))

    ResponderEliminar
  4. TheSur, todo llegará.. poco a poco :P

    ResponderEliminar