2010-02-08 7 views
76

Con el fin de hacer una sucia página (de encender el bit de daños en la entrada de tabla de páginas), toco los primeros bytes de la página como esta:¿Cómo prevenir que gcc optimice algunas afirmaciones en C?

pageptr[0] = pageptr[0]; 

Pero en la práctica GCC ignorará la declaración de muertos eliminación de tiendas Con el fin de evitar que la optimización de gcc, me re-escritura de la declaración de la siguiente manera:

volatile int tmp; 
tmp = pageptr[0]; 
pageptr[0] = tmp; 

parece que el truco funciona, pero un poco fea. Me gustaría saber si hay directivas o sintaxis que tengan el mismo efecto. Y no quiero usar una bandera -O0, ya que también traerá una gran penalización al rendimiento.

+2

¿Ha intentado -O0? –

+4

@Mark -O0 detendrá la optimización, pero también ralentizará el rendimiento del programa. Solo quiero evitar la optimización de este fragmento de código: P – ZelluX

Respuesta

65

Al desactivar la optimización se soluciona el problema, pero no es necesario. Una alternativa más segura es hacer ilegal que el compilador optimice la tienda utilizando el calificador de tipo volatile.

// Assuming pageptr is unsigned char * already... 
unsigned char *pageptr = ...; 
((unsigned char volatile *)pageptr)[0] = pageptr[0]; 

El volatile calificador de tipo indica al compilador que ser estrictos con memoria almacena y cargas. Uno de los propósitos de volatile es informar al compilador que el acceso a la memoria tiene efectos secundarios y, por lo tanto, debe conservarse. En este caso, la tienda tiene el efecto secundario de causar un error de página y desea que el compilador preserve el error de página.

De esta manera, el código circundante aún puede optimizarse, y su código es portátil para otros compiladores que no entienden la sintaxis #pragma o __attribute__ de GCC.

+1

Diría que esto es preferible a desactivar las optimizaciones. Aún puede beneficiarse de otras optimizaciones con este método. –

+0

¿De verdad necesitas hacer una carga desde la página? Seguramente solo la tienda haría: '* (volatile int *) pageptr = 0;' – caf

+0

Necesita modificar el programa que lo hará ilegible. – Phong

131

Puede utilizar

#pragma GCC push_options 
#pragma GCC optimize ("O0") 

your code 

#pragma GCC pop_options 

desactivar las optimizaciones desde GCC 4.4.

Consulte la documentación de GCC si necesita más detalles.

97

En lugar de utilizar los nuevos pragmas, también puede usar __attribute__((optimize("O0"))) para sus necesidades. Esto tiene la ventaja de solo aplicar a una sola función y no a todas las funciones definidas en el mismo archivo.

Ejemplo de uso:

void __attribute__((optimize("O0"))) foo(unsigned char data) { 
    // unmodifiable compiler code 
} 
+3

¿Qué pasa si no estoy usando la opción '-Olevel' pero utilicé las opciones individuales que se encienden por separado? * (En mi caso, no puedo determinar cuál es la opción de optimización individual que está rompiendo el código) *. – user2284570

Cuestiones relacionadas