나는 최대 수준의 경고를 받아야하는 최소한의 포함 세트를 찾았습니다. 그런 다음 목록에서 실제로 나쁜 일이 발생하고 있음을 나타내지 않거나 실제 빌드에 사용하기에는 너무 많은 오 탐지가 있다고 생각하는 일련의 경고를 제거했습니다. 내가 제외시킨 각 항목이 제외 된 이유에 대해 언급했습니다. 이것이 제가 제안한 마지막 경고입니다.
-pedantic -Wall -Wextra -Wcast-align -Wcast-qual -Wctor-dtor-privacy -Wdisabled-optimization -Wformat=2 -Winit-self -Wlogical-op -Wmissing-declarations -Wmissing-include-dirs -Wnoexcept -Wold-style-cast -Woverloaded-virtual -Wredundant-decls -Wshadow -Wsign-conversion -Wsign-promo -Wstrict-null-sentinel -Wstrict-overflow=5 -Wswitch-default -Wundef -Werror -Wno-unused
존재하는 의심스러운 경고 :
-Wno-unused
나중에 사용할 것으로 알고 있지만 아직 작성된 기능이없는 변수가 종종 있기 때문에 포함 합니다. 그것에 대한 경고를 제거하면 때때로 사물의 구현을 연기하는 선호하는 스타일로 작성할 수 있습니다. 균열을 통해 미끄러지는 것이 없는지 확인하기 위해 가끔씩 끄는 것이 유용합니다.
-Wdisabled-optimization
강력한 사용자 선호 설정 인 것 같습니다. 나는 방금 이것을 내 빌드에 추가했고 (분명한 이유로 최적화 된 빌드에만) 아무것도 나타나지 않았으므로 적어도 내가 코딩하는 방식에 대해서는 특별히 수다스러운 경고가 아닌 것 같습니다. 이 경고를 유발하는 코드가 반드시 잘못된 것은 아니지만 도구를 사용하는 대신 도구를 사용한다고 믿기 때문에 포함합니다. gcc가 내가 작성한 방식으로 코드를 최적화 할 수 없다고 말하면 다시 작성해야합니다. 나는이 경고를 유발하는 코드가 더 모듈화 된 것으로부터 이익을 얻을 수 있다고 생각합니다.
-Wfloat-equal
안전한 동등성 비교 (특히 계산되지 않은 값 -1과의 비교)에 대해 경고합니다. 이것을 사용하는 코드의 예는 float 벡터가 있다는 것입니다. 이 벡터를 살펴보면 아직 평가할 수없는 몇 가지 요소가 있으므로 -1.0f로 설정합니다 (내 문제는 양수 만 사용하므로 -1은 도메인 외부에 있음). 나중에 -1.0f 값을 업데이트합니다. 다른 작동 방법에 쉽게 적합하지 않습니다. 나는 대부분의 사람들 이이 문제를 가지고 있지 않다고 생각하고 부동 소수점에서 정확한 숫자를 비교하는 것은 아마도 오류 일 것이므로 기본 목록에 포함하고 있습니다.
-Wold-style-cast
내가 사용하는 라이브러리 코드에 많은 오 탐지가 있습니다. 특히 네트워킹에 사용되는 htonl 함수 제품군과 내가 사용중인 Rijndael (AES) 암호화 구현에는 경고하는 구식 캐스트가 있습니다. 이 두 가지를 모두 교체하려고하지만 내 코드에 불평 할만한 다른 것이 있는지 확실하지 않습니다. 하지만 대부분의 사용자는이 기능을 기본적으로 설정해야합니다.
-Wsign-conversion
힘든 일이었습니다 (그리고 거의 목록을 만들지 않았습니다). 내 코드에서 켜면 엄청난 양의 경고 (100 개 이상)가 생성되었습니다. 거의 모든 사람들이 결백했습니다. 그러나 나는 확실하지 않은 곳에서는 부호있는 정수를 사용하는 데주의를 기울 였지만, 특정 문제 영역의 경우 일반적으로 많은 양의 정수 나누기 때문에 부호없는 값을 사용하여 약간의 효율성 증가를 얻었습니다. 실수로 부호있는 정수를 부호없는 정수로 승격 한 다음 나누는 것에 대해 염려했기 때문에이 효율성을 희생했습니다 (더하기, 빼기 및 곱하기와 달리 안전하지 않음). 이 경고를 켜면 대부분의 변수를 서명되지 않은 유형으로 안전하게 변경하고 다른 위치에 몇 가지 캐스트를 추가 할 수있었습니다. 경고가 그렇게 똑똑하지 않기 때문에 현재 사용하기가 조금 어렵습니다. 예를 들어unsigned short + (integral
constant expression)
, 그 결과는 암시 적으로 int로 승격됩니다. 그런 다음 해당 값을 unsigned
또는에 할당하면 unsigned short
안전하더라도 잠재적 인 기호 문제에 대해 경고
합니다. 이것은 거의 모든 사용자에게 가장 선택적인 경고입니다.
-Wsign-promo
: 참조 -Wsign-conversion
.
-Wswitch-default
무의미 해 보입니다 (모든 가능성을 명시 적으로 열거했다면 항상 기본 케이스를 원하지는 않습니다). 그러나이 경고를 켜면 아마도 좋은 생각이 될 수 있습니다. 나열된 가능성을 제외한 모든 것을 명시 적으로 무시하려는 경우 (다른 숫자도 가능) 다음을 입력하십시오.default: break;
명시 적으로 만들 수 있습니다. 모든 가능성을 명시 적으로 열거하는 경우이 경고를 설정하면 실제로 가능한 모든 옵션을 다루 었는지 확인하기 위해 assert (false)와 같은 것을 입력하는 데 도움이됩니다. 문제의 영역이 무엇인지 명시하고 프로그래밍 방식으로 적용 할 수 있습니다. 그러나 모든 곳에서 assert (false)를 고수 할 때는주의해야합니다. 기본 케이스로 아무것도하지 않는 것보다 낫지 만 어설 션은 평소와 같이 릴리스 빌드에서는 작동하지 않습니다. 즉, 네트워크 연결이나 절대적으로 제어 할 수없는 데이터베이스에서 가져온 번호의 유효성을 검사하는 데 신뢰할 수 없습니다. 예외 또는 일찍 반환하는 것이이를 처리하는 가장 좋은 방법입니다 (하지만 여전히 기본 케이스가 있어야합니다!).
-Werror
나에게 중요한 것입니다. 다중 대상이있는 다중 스레드 빌드에서 많은 양의 코드를 컴파일 할 때 경고가 발생하기 쉽습니다. 경고를 오류로 바꾸면 경고를 알아 차릴 수 있습니다.
그런 다음 유용하다고 생각하지 않았기 때문에 위 목록에 포함되지 않은 경고 집합이 있습니다. 다음은 기본 목록에 포함하지 않는 이유에 대한 경고 및 내 의견입니다.
없는 경고 :
-Wabi
다른 컴파일러의 바이너리를 결합하지 않기 때문에 필요하지 않습니다. 어쨌든 컴파일을 시도했지만 트리거되지 않았으므로 불필요하게 장황 해 보이지 않습니다.
-Waggregate-return
내가 오류라고 생각하는 것이 아닙니다. 예를 들어, 클래스 벡터에서 범위 기반 for 루프를 사용할 때 트리거됩니다. 반환 값 최적화는 이것의 모든 부정적인 영향을 처리해야합니다.
-Wconversion
이 코드에서 트리거 : short n = 0; n += 2;
int 로의 암시 적 변환은 대상 유형으로 다시 변환 될 때 경고를 발생시킵니다.
-Weffc++
이니셜 라이저 목록에서 모든 데이터 멤버가 초기화되지 않은 경우 경고를 포함합니다. 나는 의도적으로 많은 경우에 이것을하지 않기 때문에 경고 세트가 너무 복잡해서 유용하지 않다. 하지만 가끔씩 켜고 다른 경고 (예 : 기본 클래스의 비가 상 소멸자)를 검색하는 것이 좋습니다. 이것은 -Wall
자체적으로 단일 경고 대신 경고 모음 (예 :)으로 더 유용합니다 .
-Winline
헤더에서 함수를 인라인으로 정의하기 위해 최적화 목적으로 인라인 키워드를 사용하지 않기 때문에 부재합니다. 옵티마이 저가 실제로 그것을 인라인하는지 상관하지 않습니다. 이 경고는 클래스 본문에 선언 된 함수 (예 : 빈 가상 소멸자)를 인라인 할 수없는 경우에도 표시됩니다.
-Winvalid-pch
미리 컴파일 된 헤더를 사용하지 않기 때문에 누락되었습니다.
-Wmissing-format-attribute
gnu 확장을 사용하지 않기 때문에 사용되지 않습니다. 동일 -Wsuggest-attribute
및 기타 여러
그것의 부재로 인해 잠재적으로 주목할만한 것은 -Wno-long-long
내가 필요하지 않은입니다. 정수 유형 을 포함하는 -std=c++0x
( -std=c++11
GCC 4.7에서)로 컴파일 long long
합니다. C ++ 98 / C ++ 03에 갇힌 사람들은 경고 목록에서 제외를 추가하는 것을 고려할 수 있습니다.
-Wnormalized=nfc
이미 기본 옵션이며 최고로 보입니다.
-Wpadded
클래스의 레이아웃을 최적화하기 위해 가끔 켜져 있지만 모든 클래스에 마지막 패딩을 제거 할 수있는 요소가 충분하지 않기 때문에 켜져 있지 않습니다. 이론적으로는 '무료'에 대한 추가 변수를 얻을 수 있지만이를 유지하기위한 추가 노력은 가치가 없습니다 (클래스 크기가 변경되면 이전에 사용 가능한 변수를 제거하기가 쉽지 않습니다).
-Wstack-protector
내가 사용하지 않기 때문에 사용되지 않습니다 -fstack-protector
-Wstrict-aliasing=3
에 의해 켜져 -Wall
있고 가장 정확하지만 레벨 1과 2가 더 많은 경고를 제공하는 것처럼 보입니다. 이론적으로 낮은 수준은 '더 강력한'경고이지만 더 많은 오탐을 초래합니다. 내 자신의 테스트 코드는 3 단계 모두에서 깔끔하게 컴파일되었습니다.
-Wswitch-enum
내가 원하는 행동이 아닙니다. 모든 switch 문을 명시 적으로 처리하고 싶지 않습니다. 언어에 지정된 switch 문에서이를 활성화하는 메커니즘이있는 경우 유용 할 수 있지만 (열거 형에 대한 향후 변경 사항이 필요한 모든 곳에서 처리되도록 보장하기 위해) "all-or-nothing"설정에는 과잉입니다.
-Wunsafe-loop-optimizations
잘못된 경고가 너무 많이 발생합니다. 이를 주기적으로 적용하고 결과를 수동으로 확인하는 것이 유용 할 수 있습니다. 예를 들어, 벡터의 모든 요소를 반복하여 함수 집합을 적용 할 때 (범위 기반 for 루프 사용) 내 코드에서이 경고를 생성했습니다. 또한 const std :: string의 const 배열 생성자에 대한 경고입니다 (여기서는 사용자 코드에서 루프가 없음).
-Wzero-as-null-pointer-constant
그리고 -Wuseless-cast
내가 GCC 4.7로 전환 할 때 내가 추가 할 것 GCC-4.7-경고 만입니다.
이 연구의 결과로 gcc에 몇 가지 버그 보고서 / 향상 요청을 제출 했으므로 결국 "포함하지 않음"목록의 경고를 "포함"목록에 추가 할 수 있기를 바랍니다. . 이 목록에는이 스레드에서 언급 된 모든 경고가 포함되어 있습니다 (몇 가지 추가 사항 포함). 이 게시물에서 명시 적으로 언급하지 않은 많은 경고는 제가 언급하는 또 다른 경고의 일부로 포함되어 있습니다. 이 게시물에서 완전히 제외 된 경고를 발견 한 사람이 있으면 알려주십시오.
편집 : 내가 몇 가지를 놓친 것 같습니다 (지금 추가했습니다). 실제로 잘 숨겨져 있는 http://gcc.gnu.org에 두 번째 페이지 가 있습니다. 일반 경고 옵션 및 C ++ 옵션 (경고를 보려면 아래로 스크롤)
-Wall
)가있다-Wbloody_everything
플래그 :-)