2012-02-24 10 views
6

acabo de descubrir la directiva #pragma weak en GCC:¿Cuán ampliamente compatible es pragma débil y supera los problemas de uso del atributo gcc?

6.57.9 pragmas

Para la compatibilidad con SVR4 débil, GCC soporta un conjunto de directivas #pragma para declarar símbolos a ser débil, y la definición de alias débiles .

#pragma weak symbol

Este símbolo pragma declara ser débil, como si la declaración tenía el atributo del mismo nombre. El pragma puede aparecer antes o después de la declaración del símbolo. No es un error que el símbolo nunca se defina en absoluto.

#pragma weak symbol1 = symbol2

Este pragma declara symbol1 ser un alias débil de symbol2. Es un error si symbol2 no está definido en la unidad de traducción actual.

http://gcc.gnu.org/onlinedocs/gcc/Weak-Pragmas.html

A pesar del hecho de que los desarrolladores de GCC en general, no les gusta #pragma y le animan a utilizar __attribute__ lugar para todo tipo de cosas que podrían ser pragmas, me inclino a creer que en realidad puede #pragma weak ser superior al enfoque basado en los atributos, que se parece:

extern __typeof(old_name) new_name __attribute__(weak, alias("old_name")) 

Aparte de la fealdad de requerir __typeof (o que requieren que saber el tipo y lo dicen claramente exp lícitamente, incluso si se trata de un tipo de función realmente compleja), el mayor problema del enfoque basado en atributos es que "old_name" se debe pasar a gcc como una cadena para pegar literalmente en el ensamblaje generado. Esto es problemático porque diferentes sistemas tienen diferentes características de creación de nombres (la más popular es prefijar un guión bajo en todos los nombres de símbolos C, o no hacer nada en absoluto), y para pasar la cadena correcta al atributo alias, debe conocer el nombre de manipulación convención del sistema para el que está construyendo, que en realidad no es conocimiento que pertenece a una biblioteca de nivel de aplicación donde los alias débiles podrían ser útiles.

La sintaxis #pragma weak new_name = old_name parece evitar este problema manejando ambos nombres en el nivel del compilador, donde t puede manipularlos apropiadamente, a menos que esté equivocado.

Entonces, con todos los preliminares terminados, mis preguntas reales son: ¿Me equivoco al tener #pragma weak ventaja de "portabilidad"? y ¿Todos los compiladores modernos en sistemas unix (gcc, pcc, tinycc, icc, llvm/clang, etc.) aún son compatibles con el SVR4 tradicional #pragma weak?

Soy consciente de la siguiente pregunta similar, pero no parece exactamente lo mismo y las respuestas a no tratar satisfactoriamente mi pregunta:

How portable is weak linking? #pragma weak my_symbol

Respuesta

4

Ni "#pragma débil" ni __attribute__ es parte del estándar C, por lo que tampoco es, en sentido estricto, portátil. Algunos compiladores C se esfuerzan por ser compatibles con la mayoría de las extensiones de GCC al estándar C, otros no.

Hablando en general, si ya se está hablando de símbolos débiles y alias débiles, es probable que ya haya pasado el punto en el que puede escribir código que sea confiablemente portátil entre los compiladores. Incluso su cadena de herramientas se convertirá en un problema aquí (incluyendo especialmente el enlazador). No creo que pueda confiar en nada sin una prueba cuidadosa.

Editado para agregar: El póster original comentó a continuación si, pragmáticamente, #pragma no es menos portátil que __atributo__.

Mi propia experiencia ha sido la siguiente: es agradable poder ocultar todas esas cosas dentro de las macros u otros códigos generados para facilitar la portabilidad. __attribute__ es más fácil de ocultar dentro de un archivo de encabezado de portabilidad. Por ejemplo, al menos uno de los núcleos BSD tiene un cdefs.h que usa __attribute__ dentro de una macro para centralizar la forma en que se hacen las definiciones débiles a lo largo de la base del código para permitir cambios más fáciles a los nuevos compiladores. #pragma es más difícil de usar de esa manera. una macro de este tipo también puede ocultar la diferencia entre diversos manglings nombre usando el operador CPP pegar ("##", etc.)

Para un ejemplo de tal uso, véase: http://cvsweb.netbsd.org/bsdweb.cgi/src/sys/sys/cdefs.h?rev=1.89.6.1&content-type=text/x-cvsweb-markup

+0

supongo esta respuesta puede ser es útil para algunos lectores, pero no proporciona ninguna información que yo todavía no tenga. Mi pregunta es básicamente si '#pragma weak' es * más portable que *' __attribute __ ((weak, alias)) 'o al menos * no less portable *, incluida la cuestión de si estoy en lo correcto al respecto evitando el nombre de manipulación problema. –

+1

Ninguno es portátil por ninguna medida razonable. En cuanto a si #pragma es "no menos portátil", sugeriría que probablemente no sea una buena opción, y explicaré por qué en una edición anterior. – Perry

+1

Es por eso que C99 agregó '_Pragma', que debería funcionar siempre que funcione' # pragma' ... –

Cuestiones relacionadas