2011-05-05 15 views
13

Cada vez que hago un objdump -D siempre veo el código asm con lotes de instrucciones NOP (instrucciones) que no hacen nada¿Por qué código de máquina salida de gcc tienen instrucciones nop

Por ejemplo tomar este mismo programa:

#include <stdio.h> 
#include <math.h> 

int main() 
{ 
    printf("Hello World!\n"); 
    printf("cos: %f\n", cos(1)); 
    return 1; 
} 

el objdump para exampe tiene 2 PON al final del punto

0000000000400450 <_start>: 
400450: 31 ed     xor %ebp,%ebp 
400452: 49 89 d1    mov %rdx,%r9 
400455: 5e      pop %rsi 
400456: 48 89 e2    mov %rsp,%rdx 
400459: 48 83 e4 f0    and $0xfffffffffffffff0,%rsp 
40045d: 50      push %rax 
40045e: 54      push %rsp 
40045f: 49 c7 c0 00 06 40 00 mov $0x400600,%r8 
400466: 48 c7 c1 70 05 40 00 mov $0x400570,%rcx 
40046d: 48 c7 c7 34 05 40 00 mov $0x400534,%rdi 
400474: e8 bf ff ff ff   callq 400438 <[email protected]> 
400479: f4      hlt  
40047a: 90      nop 
40047b: 90      nop 

entrada Y eso es sólo uno de muchos ejemplos, pero usted consigue la idea. ¿Por qué el código C se compila de esta manera? Gracias por adelantado.

Respuesta

7

Muy a menudo se usan para rellenar para que las cosas siguientes comiencen de nuevo en una palabra o límite, ya que el acceso a código arbitrario que no esté alineado con los límites de palabras es mucho más costoso para la CPU.

17

Se agregan nop s para forzar la próxima función alinear al límite de 4 bytes. (Observe que la dirección que sigue a la última nop será 40047c que es divisible por 4)

+0

En x86_64, también noté un nop de 4 bytes en el medio de una función (justo antes de una 'llamada'):' 0f 1f 40 00 \t nop DWORD PTR [rax + 0x0] '¿Alguna idea de para qué sirve? Ocurre en '-O3'. –

+1

@Kerrek si no recuerdo mal, le dice al procesador que borre su caché y lo vuelva a cargar con los datos en la dirección indicada. En ese caso, el procesador borrará su caché con los datos en '[rax]' (que supongo que es la dirección a la que salta la llamada). Esto permite que el procesador comience a recargar su caché con los datos correctos antes del salto. –

Cuestiones relacionadas