2009-01-23 10 views
14

En MSVC tengo esto en un encabezado:advertencias del usuario en msvc AND gcc?

#define STR(x)   #x 
#define STR2(x)   STR(x) 
#define NOTE(text)  message (__FILE__ "(" STR2(__LINE__) ") : -NOTE- " #text) 
#define noteMacro(text) message (__FILE__ "(" STR2(__LINE__) ") : " STR2(text)) 

y hago

#pragma NOTE(my warning here) 

GCC tiene:

#warning(my warning here) 

Sin embargo MSVC (2003) da un ataque cuando ve #warning y da "error fatal C1021: comando de preprocesador no válido 'advertencia'"

¿Qué puedo hacer al respecto? ¿Hay alguna manera de que GCC reconozca las advertencias de MSVC o que MSVC no arroje un error sobre las advertencias de GCC? ¿Hay algo que pueda hacer que funcione en ambos? Puedo hacer que GCC me advierta sobre pragmas desconocidos, pero esa no es la solución más ideal.

+0

¿No lo haría #ifdef? – Loki

+0

He fusionado '#ifdef _MSC_VER/GCC ...' en un solo 'PRAGMA_WARNING', http://stackoverflow.com/a/40147989/621706 – fantastory

Respuesta

15

La mejor solución que he encontrado para este problema es tener lo siguiente en una cabecera común:

// compiler_warning.h 
#define STRINGISE_IMPL(x) #x 
#define STRINGISE(x) STRINGISE_IMPL(x) 

// Use: #pragma message WARN("My message") 
#if _MSC_VER 
# define FILE_LINE_LINK __FILE__ "(" STRINGISE(__LINE__) ") : " 
# define WARN(exp) (FILE_LINE_LINK "WARNING: " exp) 
#else//__GNUC__ - may need other defines for different compilers 
# define WARN(exp) ("WARNING: " exp) 
#endif 

A continuación, utilice

#pragma message WARN("your warning message here") 

durante todo el código en lugar de #WARNING

En MSVC, obtendrá un mensaje como este:

c:\programming\some_file.cpp(3) : WARNING: your warning message here 

Bajo gcc que obtendrá:

c:\programming\some_file.cpp:25: note: #pragma message: WARNING: your warning message here 

No es perfecto, pero un compromiso razonable.

+1

Markdown no parece querer trabajar para mí, pero quería agregar que si solo admite versiones GCC compatibles con C99 y VS2008 +, puede usar la palabra clave __Pragma de GCC (por ejemplo: '__Pragma (mensaje (" ADVERTENCIA : "exp))') y la palabra clave __pragma de MSVC (por ejemplo: '__pragma (mensaje (FILE_LINE_LINK" ADVERTENCIA: "exp))') para acortar esto un poco más. Supongo que VS2008 es la versión mínima admitida, ya que es la [primera versión en MSDN] (http://msdn.microsoft.com/en-us/library/d9x1s805 (v = vs.90) .aspx) que tiene documentación que hace referencia a esta palabra clave. –

+0

Si imprime "advertencia:" en lugar de "ADVERTENCIA:" al comienzo del mensaje (después de FILE_LINE_LINK) ¡incluso aparece en la lista de errores como advertencia! – Gombat

6

Como ya ha descubierto, #warning no es una característica estándar, por lo que no puede usarlo con compiladores que no lo soportan. Si desea que su código funcione en todas las plataformas, no usará #warning en absoluto, o al menos, no en el código que MSVC está destinado a procesar (podría ser preprocesado por #ifdef o equivalente). Por lo tanto:

#ifdef __GNUC__ 
#warning(warning message) 
#else 
#pragma NOTE(warning message) 
#endif 

Pero que se repite el mensaje y estoy seguro de que tenía en mente no hacer eso - y es voluminoso; solo lo usarías muy pocas veces. También podría necesitar tratar con otros compiladores además de GCC (y no estoy lo suficientemente familiarizado con MSVC como para saber cómo identificarlo de manera confiable).

Sería bueno si se estandarizaran #warning; no está estandarizado en C99.

(había, érase hace mucho tiempo, un SO pregunta acerca de tales características que podrían añadirse a C y #warning llegó hasta allí.)

Ver también: Portability of #warning preprocessor directive

3

Guardia con # if declaraciones. Busque un símbolo definido por un compilador pero no por el otro.

#ifdef _MSC_VER 
#pragma NOTE(my warning here) 
#else 
#warning(my warning here) 
#endif 

Tipo de feo, pero no veo otra manera.

+0

Agregaste esto mientras no editaba mi respuesta y agregaba la prueba inversa. .. Supongo que _MSC_VER es la contraparte de __GNUC__! Gracias. –

+0

_MSC_VER no solo declara que está en Microsoft C++, también define qué versión está usando. –

1

Si se desea, se puede añadir a las soluciones por encima de una pequeña cosa (#pragma warning) antes su #pragma message:

#pragma warning() 
#pragma message(" SOME USER WARNING - FILE LINE etc... ") 

Este pequeño complemento genera la advertencia real, y no se ve mal en la ventana de VC. Por ejemplo:

1>e:\proj\file.h(19) : warning C4615: #pragma warning : unknown user warning type 
1> SOME USER WARNING - FILE LINE etc... 
1>proj - 0 error(s), 1 warning(s) 

Por lo general utiliza este método para advertencias no eran demasiado tranquilo, como en el código de caja sin la #pragma warning().

Por ejemplo, la forma de advertencias es demasiado silenciosa (para mí, por supuesto).

1> SOME USER WARNING - FILE LINE etc.. 
1>proj - 0 error(s), 0 warning(s) 

Sin embargo, solo una pequeña cosmética.

+0

Una forma más simple de obligar al compilador de MSVC a contar/mostrar una advertencia real es tener el texto ** ": advertencia:" ** en el mensaje de salida. – Matthew

Cuestiones relacionadas