번역 단위의 일부에 대해서만 GCC 경고를 선택적으로 비활성화 하시겠습니까?


85

이 MSVC 전 처리기 코드와 가장 가까운 GCC는 무엇입니까?

#pragma warning( push )                    // Save the current warning state.
#pragma warning( disable : 4723 )          // C4723: potential divide by 0
// Code which would generate warning 4723.
#pragma warning( pop )                     // Restore warnings to previous state.

특정 경고를 생성하지 않으려는 일반적으로 포함 된 헤더에 코드가 있습니다. 그러나 우리는 이러한 헤더를 포함하는 파일이 계속해서 경고를 생성하기를 원합니다 (프로젝트에 경고가 활성화 된 경우).


헤더가 / usr / include에 설치된 경우 또는 gcc가 기본적으로 경고를 생성하지 않습니다.
Spudd86

답변:


95

이는 GCC 버전 4.6 이후 또는 2010 년 6 월경 트렁크에서 가능합니다.

예를 들면 다음과 같습니다.

#pragma GCC diagnostic push
#pragma GCC diagnostic error "-Wuninitialized"
    foo(a);         /* error is given for this one */
#pragma GCC diagnostic push
#pragma GCC diagnostic ignored "-Wuninitialized"
    foo(b);         /* no diagnostic for this one */
#pragma GCC diagnostic pop
    foo(c);         /* error is given for this one */
#pragma GCC diagnostic pop
    foo(d);         /* depends on command line options */

8
푸시 및 팝 기능은 gcc 4.6 ( gcc.gnu.org/onlinedocs/gcc-4.6.0/gcc/Diagnostic-Pragmas.html ) 에 추가되었습니다 .
Dave Johansen 2011

1
두 번 터질 경우 두 번 밀고 싶을 것입니다.
Dan

2
@Dan : 설명서를 읽고 의견을 말하십시오. 예제의 출처를 확인하십시오.
Matt Joiner

4.4.7과 같은 이전 버전의 FYI 는 계속 사용할 수 #pragma GCC diagnostic [error|warning|ignored]있지만 pop구현 / 지원되지 않습니다.
Trevor Boyd Smith

36

가장 가까운 것은입니다 GCC 진단 프라 그마 , #pragma GCC diagnostic [warning|error|ignored] "-Wwhatever". 원하는 것과 매우 가깝지 않으며 자세한 내용과 경고는 링크를 참조하십시오.


1
이 기능을 추가하지 않은 이유가 무엇이며 어디에 있는지 알고 있습니까? (찾을 수 없었습니다.) 경고 push-disable-pop이 유용하다는 것을 알았습니다.

1
gcc에 "기능을 추가하지 않는 것"이 ​​작업 패치를 제출하는 사람이없는만큼 근거가있는 경향이 있다고는 생각하지 않습니다.
chaos

14
아무도 gcc에서 이러한 종류의 세분화 된 경고 제어를 위해 작업을 수행하거나 코드를 제출할 의향이있는 것이 아닙니다. 이미이 작업을 수행 한 주요 실리콘 밸리 회사와 누군가에게 지불 할 수있는 다른 회사를 알고 있습니다. 이를 수행하고 코드를 스트림으로 가져옵니다. 오히려 (gdb 관리자 중 한 명인)이 문제에 연결되어있는 사람과의 토론에 따르면 gcc 관리자는 "경고가 있으면 버그이므로 고쳐야합니다."라는 철학을 가지고 있습니다. 그래서 (imo) 그것은 종교적인 논쟁이고 그들은 코드를 통제하여 그들이 이깁니다.
Bob Murphy

Bob의 의견에 덧붙여, GCC 개발자는 #pragma지시문 을 싫어하는 기록이 있으므로 GCC에 특정한 모든 것이 __attribute__((foo)).
Tom

10
새로운 GCC는 (> = 4.4)가 #pragma GCC push_options방금 진단보다 더 ...에 대해 깨끗이 수 gcc.gnu.org/onlinedocs/gcc/...
Spudd86

33

비슷한 일을했습니다. 타사 코드의 경우 경고를 전혀보고 싶지 않았습니다. 그래서, 지정하기보다는 -I/path/to/libfoo/include, 내가 사용 -isystem /path/to/libfoo/include. 이로 인해 컴파일러는 경고 목적으로 해당 헤더 파일을 "시스템 헤더"로 취급하고을 활성화하지 않는 한 -Wsystem-headers대부분 안전합니다. 나는 여전히 거기에서 몇 가지 경고가 누출되는 것을 보았지만 대부분의 쓰레기를 줄였습니다.

이는 include-directory로 문제가되는 코드를 격리 할 수있는 경우 에만 도움 이 됩니다 . 자체 프로젝트의 하위 집합이거나 다른 코드와 혼합되어 있으면 운이 좋지 않습니다.


1
좋은 팁. LLVM을 사용하는 경우 "Apple LLVM 컴파일러-언어"섹션의 "기타 C 플래그"아래에 -isystem 플래그를 추가하십시오.
Nestor

@Tom 공유해 주셔서 감사합니다. 솔루션을 어디에서 사용해야하는지 이해할 수 없습니다. 조금 더 말씀해 주 시겠어요?
Lorenzo B

1

이것은 Matt Joiner의 답변에 대한 확장 입니다.

코드 전체에 pragma를 생성하지 않으려면 _Pragma 연산자를 사용할 수 있습니다 .

#ifdef __GNUC__
#  define DIAGNOSTIC_ERROR(w) _Pragma("GCC diagnostic error \"" w "\"")
#  define DIAGNOSTIC_IGNORE(w) _Pragma("GCC diagnostic ignore \"" w "\"")
#  define DIAGNOSTIC_PUSH _Pragma("GCC diagnostic push")
#  define DIAGNOSTIC_POP _Pragma("GCC diagnostic pop")
#endif
// (...)

DIAGNOSTIC_ERROR("-Wuninitialized")
foo(a); // Error

DIAGNOSTIC_PUSH
DIAGNOSTIC_IGNORE("-Wuninitialized")
foo(a); // No error

DIAGNOSTIC_POP
foo(a); // Error
당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.