2012-02-24 25 views
6

A continuación se presenta la salida de objdump de un programa de ejemplo,generación operando de instrucción CALL en x86-64 de AMD

080483b4 <display>: 
80483b4:  55      push %ebp 
80483b5:  89 e5     mov %esp,%ebp 
80483b7:  83 ec 18    sub $0x18,%esp 
80483ba:  8b 45 0c    mov 0xc(%ebp),%eax 
80483bd:  89 44 24 04    mov %eax,0x4(%esp) 
80483c1:  8d 45 fe    lea 0xfffffffe(%ebp),%eax 
80483c4:  89 04 24    mov %eax,(%esp) 
80483c7:  e8 ec fe ff ff   call 80482b8 <[email protected]> 
80483cc:  8b 45 08    mov 0x8(%ebp),%eax 
80483cf:  89 44 24 04    mov %eax,0x4(%esp) 
80483d3:  c7 04 24 f0 84 04 08 movl $0x80484f0,(%esp) 
80483da:  e8 e9 fe ff ff   call 80482c8 <[email protected]> 
80483df:  c9      leave 
80483e0:  c3      ret 

080483e1 <main>: 
80483e1:  8d 4c 24 04    lea 0x4(%esp),%ecx 
80483e5:  83 e4 f0    and $0xfffffff0,%esp 
80483e8:  ff 71 fc    pushl 0xfffffffc(%ecx) 
80483eb:  55      push %ebp 
80483ec:  89 e5     mov %esp,%ebp 
80483ee:  51      push %ecx 
80483ef:  83 ec 24    sub $0x24,%esp 
80483f2:  c7 44 24 04 f3 84 04 movl $0x80484f3,0x4(%esp) 
80483f9:  08 
80483fa:  c7 04 24 0a 00 00 00 movl $0xa,(%esp) 
8048401:  e8 ae ff ff ff   call 80483b4 <display> 
8048406:  b8 00 00 00 00   mov $0x0,%eax 
804840b:  83 c4 24    add $0x24,%esp 
804840e:  59      pop %ecx 
804840f:  5d      pop %ebp 
8048410:  8d 61 fc    lea 0xfffffffc(%ecx),%esp 

lo que tengo que entender, es en el principal vemos lo siguiente en la dirección - 8048401, llamada 80483b4, sin embargo, el código de máquina es - e8 ae ff ff ff. Veo que la instrucción CALL es E8, pero ¿cómo se decodifica la dirección de la función 80483b4 en FFFFFFAE? Hice mucha búsqueda en google pero no devolvió nada. ¿Alguien puede explicar?

Respuesta

8

E8 es el operando de "Llamada relativa", lo que significa que la dirección de destino se calcula agregando el operando a la dirección de la siguiente instrucción. El operando es 0xFFFFFFAE, que es negativo 0x52. 0x808406 - 0x52 es 0x80483b4.

La mayoría de los desensambladores calculan útilmente la dirección real del objetivo en lugar de simplemente darle la dirección relativa en el operando.

Información completa para x86 ISA en: http://www.intel.com/content/www/us/en/architecture-and-technology/64-ia-32-architectures-software-developer-vol-2a-manual.html

6

Interesante pregunta. He echado un vistazo a Intel's documentation y el código de operación E8 es CALL rel16/32. 0xffffffae es en realidad un entero con signo del complemento de dos de 32 bits igual a -82 decimal; es una dirección relativa del byte inmediatamente después del código de operación y sus operandos.

Si se hacen las cuentas se puede ver que comprueba hacia fuera:

0x8048406 - 82 = 0x80483b4

Esto pone el puntero de instrucción al principio de la función display.

+0

Gracias por sus comentarios. Entonces esto es solo para llamadas NEAR. ¿Qué hay de las llamadas FAR? De su comentario entiendo que la llamada NEAR es E8. ¿Es FAR llamado E8 también? Además, ¿el operando para la llamada FAR será abosolute? –

+0

@SamirBaid Las llamadas lejanas son '9a' y toman direcciones absolutas. También hay 'ff' que hace algo con direcciones indirectas absolutas, pero no estoy seguro de cómo funcionan. Consulte la página 716 del conjunto combinado de volúmenes (es decir, el superior) en la página que he vinculado para obtener más detalles. – spencercw

+0

@SamirBaid: Las llamadas lejanas son raras, incluso en x86_64. Las llamadas a la biblioteca generalmente se realizan a través de un PLT, por lo que necesita un segmento de texto de más de 2 GiByte para que esto suceda. – hirschhornsalz

3

llamadas Cerca suelen IP-relación - es decir, la "dirección" es en realidad un desplazamiento del puntero de instrucción. En tal caso, EIP apunta a la siguiente instrucción (por lo que su valor es 8048406). Agregue ffffffae (o -00000052 en complemento a dos), y obtendrá 80483b4.

Tenga en cuenta que toda esta matemática es de 32 bits. Aquí no está haciendo ninguna operación de 64 bits (o sus registros tendrían R s en lugar de E s en sus nombres, y las direcciones serían mucho más largas).