2010-10-13 13 views
10

dopo aver lavorato qualche tempo nel mio progetto, questo avviso cominciano ad apparire:Come prevenire macro ridefinizione

2>Game.cpp 
2>c:\program files\microsoft sdks\windows\v6.0a\include\windef.h(126) : warning C4005: 'APIENTRY' : redefinición de macro 
2>  c:\users\ferran\directo\gameprojects\dev-libs\glfw\include\glfw.h(72) : vea la definición anterior de 'APIENTRY' 
2>c:\program files\microsoft sdks\windows\v6.0a\include\wingdi.h(23) : warning C4005: 'WINGDIAPI' : redefinición de macro 
2>  c:\users\ferran\directo\gameprojects\dev-libs\glfw\include\glfw.h(88) : vea la definición anterior de 'WINGDIAPI' 

Sono sicuro che è una questione di l'ordine dei file di inclusione per risolvere, perché nessuno di questi file sono miei. La mia domanda è se esiste un modo generico per prevenire o per trovare quali file devono essere riordinati per evitare questo messaggio.

risposta

17

Il messaggio di errore si sta dicendo l'ordine corretto. Dice che windef.h e wingdi.h stanno ridefinendo i simboli definiti in glfw.h.

Inserire glfw.h dopo i file di inclusione di Windows.

+2

Questa è una buona risposta, perché è una soluzione generale o almeno un buon punto di partenza per risolvere questo tipo di problemi. – Killrazor

7

Il problema è nel file Game.cpp. Prova a includere windows.h prima del glfw.h. C'è una guardia in glfw.h che impedirà di avvertimento:

#ifndef APIENTRY 
#ifdef _WIN32 
    #define APIENTRY __stdcall 
#else 
    #define APIENTRY 
#endif 
#define GL_APIENTRY_DEFINED 
#endif // APIENTRY 
2

Sfortunatamente o fortunatamente no. Non esiste uno strumento di questo tipo che lo automatizzi. Devi andare a leggere il codice in quei file di intestazione, capire cosa sta succedendo e prendere le azioni appropriate.

Il massimo che si può fare è

  1. Controllare se la macro è definita utilizzando ifdef o if defined(...) or if !defined(...) costrutti del preprocessore.
  2. Undefine macro utilizzando undef.

Solo ANSI C considera la ridefinizione della macro un errore.

+1

Leggere il capitolo "macro replacement" in entrambi i documenti stanard C99 e C11. Entrambi affermano che la macro non deve essere ridefinita a meno che gli elenchi di sostituzione non siano identici. Quindi penso che tu abbia torto che non è considerato un errore. La verità è che molti __compiler generano solo un avvertimento, ma questo è il loro modo di trattare il codice non compilato. –

7

Microsoft generalmente non progetta intestazioni per essere indipendenti. La maggior parte delle intestazioni orientate a Windows richiede che tu abbia prima incluso <windows.h>. Tranne la dipendenza da quella Madre di tutte le intestazioni, di solito non ci sono specifiche dipendenze dell'intestazione quindi includendo <windows.h> non dovresti avere alcun problema.

+1

Tuttavia, ci sono delle eccezioni. Ad esempio, winsock2.h deve essere incluso per primo per impedire l'inclusione di winsock.h da windows.h –

+0

@ PawełStankowski: Grazie! Mi è sembrato che ci fosse una macro che controlla gli include, quindi ho attivato un Visual Studio (per caso 2012), che ha una bella funzione di go-to-header. Oh, vedo solo due possibilità: usare la guardia include interna '_WINSOCKAPI_', che è sporca, o usando' WIN32_LEAN_AND_MEAN'.Quest'ultima è pratica quasi normale, quindi dovrebbe essere buona. –

+0

Va bene come soluzione alternativa, se non hai bisogno di alcuna funzionalità dietro magra e Intendi definisce o si è sicuri che il codice non sarà utilizzato dal progetto che richiede funzionalità da windows.h ed è nascosto da WIN32_LEAN_AND_MEAN definire. –

1

Questo potrebbe essere causato dalle intestazioni di pre-compilazione di Visual Studio. Assicurati che tutte le intestazioni standard e Microsoft siano incluse prima delle tue. Non includere le intestazioni Microsoft in nessuno dei tuoi file .h (sembra che tu abbia windef.h e wingdi.h inclusi nel tuo glfw.h). Assicurati che tutte le intestazioni siano prive di effetti collaterali. Il problema dovrebbe quindi andare via. Capire esattamente cosa lo causa è generalmente molto difficile.

+0

FYI, glfw.h è un'API per OpenGL. _Nessuno_ può cambiare API. : P – Tqn