Mismatched `#pragma clang diagnostic push` suppresses deprecation warnings from system headers
- Dominant language
- LLVM
- Stars
- 40.5k
- Forks
- 18.7k
- PR merge metrics
- PR metrics pending
Description
A mismatched `#pragma clang diagnostic push` (without a corresponding pop) silently suppresses `-Wdeprecated-declarations` warnings for deprecated class template specializations in system headers. Adding a pop at the end of the file causes the warning to appear.
% cat dep.h
```
#ifndef DEP_H
#define DEP_H
#pragma clang system_header
template
struct __attribute__((deprecated("use something else"))) DepConverter {
int convert(int x) { return x + 1; }
};
struct DefaultCodec {};
template
struct Wrapper {
int run() {
DepConverter d;
return d.convert(42);
}
};
#endif
```
% cat test.cpp
```
// RUN: %clang_cc1 -fsyntax-only -Wdeprecated-declarations -verify %s
// RUN: %clang_cc1 -fsyntax-only -Wdeprecated-declarations -verify -DTRAILING_POP %s
#include "dep.h"
int foo() {
Wrapper w;
return w.run(); // #inst
}
#pragma clang diagnostic push
#pragma clang diagnostic ignored "-Wpass-failed"
#ifdef TRAILING_POP
// expected-warning@dep.h:15 {{'DepConverter' is deprecated}}
// expected-note@#inst {{in instantiation of member function 'Wrapper::run' requested here}}
// expected-note@dep.h:6 {{'DepConverter' has been explicitly marked deprecated here}}
#pragma clang diagnostic pop
#else
// expected-no-diagnostics
#endif
```
% clang++ -Wdeprecated-declarations -fsyntax-only test.cpp (no output — warning incorrectly suppressed)
% clang++ -Wdeprecated-declarations -fsyntax-only -DTRAILING_POP test.cpp dep.h:15:9: warning: 'DepConverter' is deprecated: use something else [-Wdeprecated-declarations]
The conditions to trigger this are:
- The deprecated entity is a class template specialization in a system header
- The template is instantiated from user code
- There is a mismatched #pragma clang diagnostic push (the ignored warning doesn't need to be related to deprecation)
Additionally, there is no warning for a push without a matching pop, which makes this hard to catch.
Contributor guide
Research direction
Start by running the reproducer in dep.h and test.cpp with clang++ and both settings of TRAILING_POP. Trace how diagnostic push/pop state is handled while the class template specialization is instantiated from user code and marked as coming from a system header. Done means the regression is covered by the reproducer and the deprecated-use warning is no longer silently suppressed by an unmatched push.
Written by the indexing model from the issue text.
Assessment
- Tech stack
- cpp
- Domain
- compilers
- Issue type
- Bug
- Difficulty
- 4/5
- Estimated time
- 3-5 days
- Activity status
- Quiet
- Clarity
- Mostly clear
- Newbie friendliness
- 48/100