web-dev-qa-db-fra.com

Meilleur niveau d'avertissement du compilateur pour les compilateurs C / C ++?

Quel niveau d'avertissement du compilateur recommandez-vous pour différents compilateurs C/C++?

gcc et g ++ vous permettront de vous en sortir avec beaucoup sur le niveau par défaut. Je trouve que le meilleur niveau d'avertissement pour moi est "-Wall". Et j'essaie toujours de supprimer le code pour les avertissements qu'il génère. (Même les idiots à propos de l'utilisation de parenthèses pour les règles de priorité logique ou pour dire que je veux vraiment dire "si (x = y)")

Quels sont vos niveaux préférés pour les différents compilateurs, tels que Sun CC, aCC (HPUX?), Visual Studio, Intel?

Éditer:

Je voulais juste souligner que je n'utilise pas "-Werror" (mais je comprends son utilité) sur gcc/g ++ car, j'utilise:

 # avertissement "ceci est une note pour moi" 

à quelques endroits dans mon code. Tous les compilateurs comprennent-ils la macro #warning?

45
Juan

Ceci est un ensemble de drapeaux extra-paranoïaques que j'utilise pour le code C++:

    -g -O -Wall -Weffc++ -pedantic  \
    -pedantic-errors -Wextra -Waggregate-return -Wcast-align \
    -Wcast-qual  -Wchar-subscripts  -Wcomment -Wconversion \
    -Wdisabled-optimization \
    -Werror -Wfloat-equal  -Wformat  -Wformat=2 \
    -Wformat-nonliteral -Wformat-security  \
    -Wformat-y2k \
    -Wimplicit  -Wimport  -Winit-self  -Winline \
    -Winvalid-pch   \
    -Wunsafe-loop-optimizations  -Wlong-long -Wmissing-braces \
    -Wmissing-field-initializers -Wmissing-format-attribute   \
    -Wmissing-include-dirs -Wmissing-noreturn \
    -Wpacked  -Wpadded -Wparentheses  -Wpointer-arith \
    -Wredundant-decls -Wreturn-type \
    -Wsequence-point  -Wshadow -Wsign-compare  -Wstack-protector \
    -Wstrict-aliasing -Wstrict-aliasing=2 -Wswitch  -Wswitch-default \
    -Wswitch-enum -Wtrigraphs  -Wuninitialized \
    -Wunknown-pragmas  -Wunreachable-code -Wunused \
    -Wunused-function  -Wunused-label  -Wunused-parameter \
    -Wunused-value  -Wunused-variable  -Wvariadic-macros \
    -Wvolatile-register-var  -Wwrite-strings

Cela devrait vous donner quelque chose pour commencer. Selon un projet, vous devrez peut-être l'atténuer pour ne pas voir d'avertissement provenant de bibliothèques tierces (qui sont généralement assez insouciantes de ne pas être averti.) Par exemple, le code vectoriel/matrice Boost fera émettre g ++ beaucoup du bruit.

Une meilleure façon de gérer de tels cas est d'écrire un wrapper autour de g ++ qui utilise toujours des avertissements optimisés mais qui permet de les empêcher d'être vus pour des fichiers/numéros de ligne spécifiques. J'ai écrit un tel outil il y a longtemps et je le publierai une fois que j'aurai le temps de le nettoyer.

46

Sur Visual C++, j'utilise /W4 et /WX (traite les avertissements comme des erreurs).

VC a également /Wall, mais il est incompatible avec les en-têtes standard.

Je choisis de traiter les avertissements comme des erreurs, car cela m'oblige à les corriger. Je corrige tous les avertissements, même si cela signifie ajouter #pragma pour ignorer l'avertissement - de cette façon, je déclare explicitement, que je suis au courant de l'avertissement (afin que les autres développeurs ne m'envoient pas de courrier électronique à ce sujet).

24
Paulius

Je crois que VC prend également en charge

#pragma message ("note to self")

Mais au fur et à mesure que le système se développe et se développe, et que vous obtenez une compilation nocturne sur laquelle 30 développeurs travaillent simultanément, cela prend des jours pour lire toutes les notes à soi-même, même dans la mesure où il ne fera rien d'autre que la lecture de notes et enfin briser sous le stress de ne pas pouvoir suivre et de démissionner ...

Non vraiment, le nombre d'avertissements va rapidement augmenter si vous les autorisez, et vous ne pourrez pas repérer les plus importants (variables non initialisées, ce pointeur utilisé dans le constructeur, ...).

C'est pourquoi j'essaie de traiter les avertissements comme des erreurs: la plupart du temps, le compilateur a raison de m'avertir, et s'il ne le fait pas, je le documente dans le code et je le précède

#pragma warning ( Push )
#pragma warning ( 4191 : disable )
// violent code, properly documented
#pragma warning ( pop )

I il suffit de lire ils ont aussi un pragma warning ( N : suppress ).

13
xtofl

J'ai tendance à utiliser -Wall (parce que tout le monde fait des bugs, personne n'est parfait), mais je n'utilise pas -Werror (traite les avertissements comme des erreurs) car de temps en temps gcc met en garde contre les choses qui sont correctes de toute façon (faux positifs).

9

Je suis d'accord avec litb pour toujours utiliser -Wall. De plus, si vous voulez vous assurer que votre code est conforme, vous pouvez également utiliser -pedantic. Un autre avertissement qui peut être utile si vous gérez des unions et des structures au niveau des octets est -Wpadded.

8
codelogic

Je fais tout le développement avec Warning as Errors activé.

Depuis que je développe encore dans VC6, j'ai beaucoup de # pragma dans mon code (4786 principalement).

4
graham.reeds

Sur GCC, j'utilise de préférence -Wall -Wextra -Wwrite-strings -Werror, et spécifiez également une norme avec std=. Quelle norme dépend du projet: principalement de la façon dont il doit être portable.

La raison pour laquelle j'utilise -Werror est que les avertissements sont inacceptables (pour moi) même s'ils ne représentent pas un vrai bug. Je préfère contourner la cause de l'avertissement que d'ignorer les avertissements chaque fois que je compile pour le reste de ma vie. Une fois que vous autorisez les avertissements dans la compilation, il est tout simplement trop facile d'en manquer un qui n'était pas là la dernière fois.

Bien sûr, lorsque vous traitez avec du code tiers, vous ne pouvez parfois pas vous débarrasser des avertissements. Ensuite, je déciderais au cas par cas de détendre le -W options, supprimer -Werror et écrire un script pour vérifier que seuls des avertissements sont attendus, ou peut-être modifier le code tiers (soit pour "corriger" l'avertissement, soit pour le désactiver avec des pragmas si possible).

3
Steve Jessop

personne n'a encore mentionné le compilateur Intel:

https://software.intel.com/sites/products/documentation/doclib/iss/2013/compiler/cpp-lin/GUID-D060680A-1A18-4574-8291-5C74E6E31335.htm

-w3 est assez bavard, donc je suggère -w2

3
Rob Latham

J'aime les murs et les prototypes stricts ainsi que les définitions de fonctions implicites. Les erreurs sur ceux-ci peuvent être très utiles. Il y a aussi -Wextra qui ramassera tout sortes de choses comme des choses que vous aviez l'intention d'être conditionnelles mais écrites accidentellement comme des déclarations:

if (something);
   classic_way_to_leak_memory();

Sur les systèmes de type Unix, vous devez obéir aux préférences ENV de l'utilisateur .. donc ce qu'il voit et rapporte peut être entièrement différent de ce dont vous avez besoin :)

Je suis également un fétiche de type, donc j'ai tendance à définir également -Fno-strict-aliasing, sauf si l'utilisateur le veut. Sinon, la gestion de la mémoire en C classique est difficile à réaliser.

3
Tim Post

Il y a une belle liste d'options pour GCC ici: http://mces.blogspot.com/2008/12/year-end-cleaning-ie-on-warning-options.htm . -Le mur n'active pas tous les avertissements possibles, et certains doivent être activés explicitement.

3
Marco

Dans Visual C, j'utilise/w3. Je trouve que w4 émet trop de bruit (beaucoup provenant des bibliothèques MS) pour passer par chaque build. Les avertissements supplémentaires sont très mineurs et n'ont jusqu'à présent pas été à l'origine d'un bug.

1
Patrick

J'aime aussi vérifier tous les avertissements possibles que donne le compilateur dans mon projet. Malheureusement, la réponse sur Intel C++ le compilateur n'était pas très informative pour moi (le lien est mort). J'ai fait mes propres recherches.

Parce que j'utilise Qt 5 et qmake j'ai un niveau d'avertissement prédéfini - w1 . Je ne peux rien faire avec ça. Mais ce n'est pas tout et ICC a plus de clés:

-Wcomment 
-Weffc++ 
-Wextra-tokens 
-Wformat 
-Winline // don't use, show only for example
-Wmain 
-Wmissing-declarations 
-Wmissing-prototypes 
-Wnon-virtual-dtor 
-Wp64 
-Wpointer-arith 
-Wremarks 
-Wreturn-type 
-Wsign-compare 
-Wstrict-aliasing 
-Wstrict-prototypes 
-Wtrigraphs 
-Wuninitialized 
-Wunknown-pragmas 
-Wunused-variable

En savoir plus sur tous touches .

Je veux également ajouter que, contrairement à GCC, ICC produit plusieurs avertissements pour une clé, par exemple clé - Weffc ++ . Dans le cas où vous ne souhaitez voir que plusieurs avertissements de toutes les listes, utilisez la touche - wd .

Je désactive: - wd1418,2012,2015,2017,2022,2013 . Et les avertissements - wd1572,873,2259,2261 étaient désactivés par défaut dans qmake.

J'utilise PCH et j'ai trouvé très ennuyeux de voir dans Qt Creator des messages sur l'utilisation du fichier PCH comme une erreur. Pour désactiver, utilisez - Wno-pch-messages .

Pour désactiver l'avertissement dans le code, j'utilise:

#if defined(Q_CC_INTEL)
    #pragma warning( Push )
    #pragma warning( disable: 2021 )
#endif

// some code

#if defined(Q_CC_INTEL)
    #pragma warning( pop )
#endif
1
dismine

Merci à tous pour leurs réponses. Cela fait un moment que je n'ai pas utilisé autre chose que gcc/g ++. Ceux que j'ai dû utiliser il y a longtemps sont

. espace de noms) 

Je me souviens que (il y a au moins 5 ans) tout ce qui dépassait le niveau d'avertissement par défaut du compilateur Sun Workshop CC était trop. Je pense également que cela a pu être vrai pour le compilateur Intel. Je n'ai pas été à jour avec les compilateurs non GNU depuis un moment.

0
Juan

Les compilateurs GCC deviennent plus stricts avec chaque nouvelle version. Utilisez le drapeau -ansi pour émettre des avertissements en cas de violation de l'interprétation la plus stricte des normes linguistiques ANSI. Il s'agit généralement de choses qui se produisent juste dans votre compilateur actuel, mais peuvent produire des erreurs dans la prochaine version ou dans d'autres compilateurs. Ce drapeau vous aidera à éviter d'avoir à porter votre code chaque fois que vous changez de compilateur/version.

0
palm3D