From a192afe35b579f42a2e265383d1b82fe917c0fe3 Mon Sep 17 00:00:00 2001 From: Greg Burd Date: Sun, 26 Jul 2026 13:30:36 -0400 Subject: [PATCH] Don't use __builtin_setjmp on aarch64 MinGW/Windows Commit 146cb3889c3 made the WIN32/MinGW-64 build use gcc's __builtin_setjmp/__builtin_longjmp to work around longstanding issues in MinGW-64's own setjmp support. That workaround is fine on x86_64 MinGW, but it is broken on aarch64 (ARM64) MinGW toolchains: * clang for aarch64-w64-windows-gnu does not implement __builtin_setjmp at all -- it errors with "__builtin_setjmp is not supported for the current target"; and * where the builtin is accepted its first argument is a void **, which is incompatible with the intptr_t sigjmp_buf[5] that c.h declares, producing "incompatible pointer types passing 'sigjmp_buf' to parameter of type 'void **'". The net effect is that a PostgreSQL build with a clang-based aarch64 MinGW toolchain fails to compile as early as src/common/pg_get_line.c (the first caller of sigsetjmp()). Restrict the __builtin_setjmp path to !defined(__aarch64__) so that aarch64 MinGW falls back to plain setjmp()/longjmp(), the same path already used for non-MinGW Windows toolchains. x86_64 MinGW is unchanged. Reported while building for aarch64 Windows with an MSYS2 clangarm64 toolchain. --- src/include/c.h | 13 +++++++++---- 1 file changed, 9 insertions(+), 4 deletions(-) diff --git a/src/include/c.h b/src/include/c.h index 20cfbac54e718..981f8c42f5503 100644 --- a/src/include/c.h +++ b/src/include/c.h @@ -1525,18 +1525,23 @@ typedef struct pg_signal_info * When there is no sigsetjmp, its functionality is provided by plain * setjmp. We now support the case only on Windows. However, it seems * that MinGW-64 has some longstanding issues in its setjmp support, - * so on that toolchain we cheat and use gcc's builtins. + * so on that toolchain we cheat and use gcc's builtins. That workaround + * only applies to x86_64 MinGW: on aarch64 (ARM64) MinGW toolchains + * clang does not implement __builtin_setjmp/__builtin_longjmp at all + * ("__builtin_setjmp is not supported for the current target"), and its + * prototype takes a void ** rather than PostgreSQL's sigjmp_buf, so fall + * back to plain setjmp there. */ #ifdef WIN32 -#ifdef __MINGW64__ +#if defined(__MINGW64__) && !defined(__aarch64__) typedef intptr_t sigjmp_buf[5]; #define sigsetjmp(x,y) __builtin_setjmp(x) #define siglongjmp __builtin_longjmp -#else /* !__MINGW64__ */ +#else /* !__MINGW64__ || __aarch64__ */ #define sigjmp_buf jmp_buf #define sigsetjmp(x,y) setjmp(x) #define siglongjmp longjmp -#endif /* __MINGW64__ */ +#endif /* __MINGW64__ && !__aarch64__ */ #endif /* WIN32 */ /* /port compatibility functions */