c gcc attributes const gnu

__attribute__((const)) vs__attribute__((puro)) en GNU C



gcc attributes (3)

De la documentación para el compilador ARM (que se basa en gcc):

__attribute__((pure)) atributo de función
Muchas funciones no tienen efectos, excepto devolver un valor, y su valor de retorno depende solo de los parámetros y las variables globales. Las funciones de este tipo pueden estar sujetas a análisis de flujo de datos y podrían eliminarse.

__attribute__((const)) atributo de función
Muchas funciones examinan solo los argumentos que se les pasan y no tienen efectos, excepto el valor de retorno. Esta es una clase mucho más estricta que __attribute__((pure)) , porque una función no tiene permiso para leer la memoria global. Si se sabe que una función opera solo en sus argumentos, entonces puede estar sujeta a la eliminación de subexpresiones y optimizaciones de bucle comunes.

Entonces, TL; DR: __attribute__((const)) es lo mismo que __attribute__((pure)) pero sin ningún acceso a las variables globales.

¿Cuál es la diferencia entre __attribute__((const)) y __attribute__((pure)) en GNU C?

__attribute__((const)) int f() { /* ... */ return 4; }

vs

__attribute__((pure)) int f() { /* ... */ return 4; }


La diferencia se explica en los manuales del CCG . Más notablemente, una función const solo puede usar los argumentos pasados ​​y no cualquier memoria, mientras que una función pure puede acceder a la memoria, bajo restricciones:

El atributo puro prohíbe que una función modifique el estado del programa que es observable por otros medios que no sean la inspección del valor de retorno de la función. Sin embargo, las funciones declaradas con el atributo puro pueden leer de forma segura cualquier objeto no volátil y modificar el valor de los objetos de una manera que no afecte su valor de retorno o el estado observable del programa.

El __attribute__ ((pure)) significa que la función no tiene efectos secundarios y el valor devuelto depende de los argumentos y del estado de las variables globales. Por lo tanto, es seguro para el optimizador eludir algunas llamadas, si los argumentos son los mismos, y la persona que llama no hizo nada para cambiar el estado de los globales entre las llamadas .

El __attribute__ ((const)) significa que el valor de retorno es únicamente una función de los argumentos, y si alguno de los argumentos son punteros, entonces los punteros no deben ser desreferenciados .

Una función const siempre es pure .

Ejemplos de funciones const serían las funciones abs de <stdlib.h> y algunas funciones matemáticas de <math.h> : sqrt , exp , etc. (aunque podrían estar sujetas a modos de redondeo).

Ejemplos de funciones pure pero no constantes serían funciones tales como strlen , ya que desreferencia el puntero pasado.


Tenga en cuenta que si se pasa un puntero a una función y se examinan los contextos de ese puntero, no se puede declarar const , incluso si el puntero pasado y los contextos de puntero son const . Esta es una limitación severa a la utilidad de const .

Puede devolver múltiples valores en C usando una estructura, lo que hace que sea más fácil usar pure . (Es más típico usar operandos de retorno de puntero, pero esto rompe el uso de pure ).