Skip to content

GCC PCH Breakage Triggered by fmt Scoped #pragma GCC optimize("Og") #4757

@bc-lee

Description

@bc-lee

fmt uses a scoped optimization pragma in include/fmt/base.h:

FMT_PRAGMA_GCC(push_options)
#if !defined(__OPTIMIZE__) && !defined(__CUDACC__) && !defined(FMT_MODULE)
FMT_PRAGMA_GCC(optimize("Og"))
#endif
...
FMT_PRAGMA_GCC(pop_options)

This is correct in normal compilation. However, with GCC + PCH, this can leave the compiler in an inconsistent state after PCH restore and break unrelated code.

Example failure:
error: the last argument must be an 8-bit immediate
from _mm_srli_si128(x, 2) in <emmintrin.h>.

The same code compiles fine without PCH.

Related Bugs

I originally reported as GCC bug(RHBZ 2457604): https://bugzilla.redhat.com/show_bug.cgi?id=2457604

Also similar bug report in GCC bugzilla: https://gcc.gnu.org/bugzilla/show_bug.cgi?id=105120

Similar bug report suggest that #pragma GCC optimize state is not fully or consistently restored across PCH boundaries.

Workarounds

Current options are:

  • avoid using PCH with affected GCC versions
  • avoid affected GCC versions

Proposed Workaround in fmt

Please add an opt-out macro to disable the optimization pragma:

#if !defined(FMT_DISABLE_DEBUG_OPTIMIZE_PRAGMA)
FMT_PRAGMA_GCC(push_options)
#if !defined(__OPTIMIZE__) && !defined(__CUDACC__) && !defined(FMT_MODULE)
FMT_PRAGMA_GCC(optimize("Og"))
#endif
#endif // !defined(FMT_DISABLE_DEBUG_OPTIMIZE_PRAGMA)
...
#if !defined(FMT_DISABLE_DEBUG_OPTIMIZE_PRAGMA)
FMT_PRAGMA_GCC(pop_options)
#endif // !defined(FMT_DISABLE_DEBUG_OPTIMIZE_PRAGMA)

Rationale

  • This is a QoI/debug optimization, not required for correctness
  • Default behavior remains unchanged
  • Provides a reliable escape hatch for GCC + PCH users
  • Avoids forcing users to drop PCH or fmt usage

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions