Created attachment 42239 [details] reproducer for "Incorrect _Pragma expansion in complex macro expressions"; compile with -Wall -Wextra Basically, _Pragma's expansions (as shown with gcc -E) seem to get shifted out of some slightly "more complex" macro expressions, which renders them ineffective. Attached is one piece of code that reproduces the problem. When compiled with `-Wall -Wextra`, the warning which should've been silenced isn't, because the #pragma push-pop pair gets shifted out of the expression. It's hard to pinpoint exactly what causes this, and the problem goes away with minor complexity reductions (such as replacing a macro (e.g., the tof macro) with what it expands to), but it seems to stick in more complex contexts. clang handles everything fine.
This problem still persists in gcc 7.3.0. It appears pasting a macro containing `_Pragma`s into another macro is what's causing the displacement of the generated `#pragma`s. I've cleaned up the example to make it clearer: #define PRAGMA(...) _Pragma(#__VA_ARGS__) #define PASTE(Expr) Expr #define PUSH_IGN(X) PRAGMA(GCC diagnostic push) PRAGMA(GCC diagnostic ignored X) #define POP() PRAGMA(GCC diagnostic pop) #define SIGNED_EH(X) \ ({ PUSH_IGN("-Wtype-limits") \ _Bool SIGNED_EH = ((__typeof(X))-1 < 0); \ POP() \ SIGNED_EH; }) int main(); { unsigned x; SIGNED_EH(x); //OK; #pragmas generated around the assignment: #if 0 //generated: ({ #pragma GCC diagnostic push #pragma GCC diagnostic ignored "-Wtype-limits" _Bool SIGNED_EH = ((__typeof(x))-1 < 0); #pragma GCC diagnostic pop SIGNED_EH; }); #endif PASTE(SIGNED_EH(x)); //OOPS generates: #if 0 //generated: #pragma GCC diagnostic push #pragma GCC diagnostic ignored "-Wtype-limits" #pragma GCC diagnostic pop ({ _Bool SIGNED_EH = ((__typeof(x))-1 < 0); SIGNED_EH; }); #endif } Clang's preprocessor generates correct code even for the `PASTE(SIGNED_EH(x))` case.
Depending which variant of the test you look at, this ended up getting resolved by r12-4797 and/or by r12-5454. It is the same issue as bug 102409 and bug 90400. The testcase from this PR seems worth adding in addition, so I will do that prior to closing this one. Patch adding the testcase submitted for review here: https://gcc.gnu.org/pipermail/gcc-patches/2023-October/631814.html
The master branch has been updated by Lewis Hyatt <lhyatt@gcc.gnu.org>: https://gcc.gnu.org/g:202a214d6859d91af5a95aa989321c5d2173c40a commit r14-4747-g202a214d6859d91af5a95aa989321c5d2173c40a Author: Lewis Hyatt <lhyatt@gmail.com> Date: Mon Oct 2 14:56:58 2023 -0400 libcpp: testsuite: Add test for fixed _Pragma bug [PR82335] This PR was fixed by r12-4797 and r12-5454. Add test coverage from the PR that is not represented elsewhere. gcc/testsuite/ChangeLog: PR preprocessor/82335 * c-c++-common/cpp/diagnostic-pragma-3.c: New test.
Closing it now that the testcase has been added.