Skip to content

Commit e0d4123

Browse files
committed
Suppress warning about stack_base_ptr with late-model GCC.
GCC 12 complains that set_stack_base is storing the address of a local variable in a long-lived pointer. This is an entirely reasonable warning (indeed, it just helped us find a bug); but that behavior is intentional here. We can work around it by using __builtin_frame_address(0) instead of a specific local variable; that produces an address a dozen or so bytes different, in my testing, but we don't care about such a small difference. Maybe someday a compiler lacking that function will start to issue a similar warning, but we'll worry about that when it happens. Patch by me, per a suggestion from Andres Freund. Back-patch to v12, which is as far back as the patch will go without some pain. (Recently-established project policy would permit a back-patch as far as 9.2, but I'm disinclined to expend the work until GCC 12 is much more widespread.) Discussion: https://postgr.es/m/3773792.1645141467@sss.pgh.pa.us
1 parent af2d484 commit e0d4123

File tree

7 files changed

+88
-2
lines changed

7 files changed

+88
-2
lines changed

config/c-compiler.m4

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -396,6 +396,28 @@ fi])# PGAC_CHECK_BUILTIN_FUNC
396396

397397

398398

399+
# PGAC_CHECK_BUILTIN_FUNC_PTR
400+
# -----------------------
401+
# Like PGAC_CHECK_BUILTIN_FUNC, except that the function is assumed to
402+
# return a pointer type, and the argument(s) should be given literally.
403+
# This handles some cases that PGAC_CHECK_BUILTIN_FUNC doesn't.
404+
AC_DEFUN([PGAC_CHECK_BUILTIN_FUNC_PTR],
405+
[AC_CACHE_CHECK(for $1, pgac_cv$1,
406+
[AC_LINK_IFELSE([AC_LANG_PROGRAM([
407+
void *
408+
call$1(void)
409+
{
410+
return $1($2);
411+
}], [])],
412+
[pgac_cv$1=yes],
413+
[pgac_cv$1=no])])
414+
if test x"${pgac_cv$1}" = xyes ; then
415+
AC_DEFINE_UNQUOTED(AS_TR_CPP([HAVE$1]), 1,
416+
[Define to 1 if your compiler understands $1.])
417+
fi])# PGAC_CHECK_BUILTIN_FUNC_PTR
418+
419+
420+
399421
# PGAC_PROG_VARCC_VARFLAGS_OPT
400422
# -----------------------
401423
# Given a compiler, variable name and a string, check if the compiler

configure

Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15763,6 +15763,46 @@ cat >>confdefs.h <<_ACEOF
1576315763
#define HAVE__BUILTIN_POPCOUNT 1
1576415764
_ACEOF
1576515765

15766+
fi
15767+
# __builtin_frame_address may draw a diagnostic for non-constant argument,
15768+
# so it needs a different test function.
15769+
{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for __builtin_frame_address" >&5
15770+
$as_echo_n "checking for __builtin_frame_address... " >&6; }
15771+
if ${pgac_cv__builtin_frame_address+:} false; then :
15772+
$as_echo_n "(cached) " >&6
15773+
else
15774+
cat confdefs.h - <<_ACEOF >conftest.$ac_ext
15775+
/* end confdefs.h. */
15776+
15777+
void *
15778+
call__builtin_frame_address(void)
15779+
{
15780+
return __builtin_frame_address(0);
15781+
}
15782+
int
15783+
main ()
15784+
{
15785+
15786+
;
15787+
return 0;
15788+
}
15789+
_ACEOF
15790+
if ac_fn_c_try_link "$LINENO"; then :
15791+
pgac_cv__builtin_frame_address=yes
15792+
else
15793+
pgac_cv__builtin_frame_address=no
15794+
fi
15795+
rm -f core conftest.err conftest.$ac_objext \
15796+
conftest$ac_exeext conftest.$ac_ext
15797+
fi
15798+
{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $pgac_cv__builtin_frame_address" >&5
15799+
$as_echo "$pgac_cv__builtin_frame_address" >&6; }
15800+
if test x"${pgac_cv__builtin_frame_address}" = xyes ; then
15801+
15802+
cat >>confdefs.h <<_ACEOF
15803+
#define HAVE__BUILTIN_FRAME_ADDRESS 1
15804+
_ACEOF
15805+
1576615806
fi
1576715807

1576815808
ac_fn_c_check_func "$LINENO" "fseeko" "ac_cv_func_fseeko"

configure.in

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1724,6 +1724,9 @@ PGAC_CHECK_BUILTIN_FUNC([__builtin_bswap64], [long int x])
17241724
PGAC_CHECK_BUILTIN_FUNC([__builtin_clz], [unsigned int x])
17251725
PGAC_CHECK_BUILTIN_FUNC([__builtin_ctz], [unsigned int x])
17261726
PGAC_CHECK_BUILTIN_FUNC([__builtin_popcount], [unsigned int x])
1727+
# __builtin_frame_address may draw a diagnostic for non-constant argument,
1728+
# so it needs a different test function.
1729+
PGAC_CHECK_BUILTIN_FUNC_PTR([__builtin_frame_address], [0])
17271730

17281731
AC_REPLACE_FUNCS(fseeko)
17291732
case $host_os in

src/backend/postmaster/postmaster.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1207,7 +1207,7 @@ PostmasterMain(int argc, char *argv[])
12071207
/*
12081208
* Set reference point for stack-depth checking.
12091209
*/
1210-
set_stack_base();
1210+
(void) set_stack_base();
12111211

12121212
/*
12131213
* Initialize pipe (or process handle on Windows) that allows children to

src/backend/tcop/postgres.c

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3210,7 +3210,9 @@ ia64_get_bsp(void)
32103210
pg_stack_base_t
32113211
set_stack_base(void)
32123212
{
3213+
#ifndef HAVE__BUILTIN_FRAME_ADDRESS
32133214
char stack_base;
3215+
#endif
32143216
pg_stack_base_t old;
32153217

32163218
#if defined(__ia64__) || defined(__ia64)
@@ -3220,8 +3222,16 @@ set_stack_base(void)
32203222
old = stack_base_ptr;
32213223
#endif
32223224

3223-
/* Set up reference point for stack depth checking */
3225+
/*
3226+
* Set up reference point for stack depth checking. On recent gcc we use
3227+
* __builtin_frame_address() to avoid a warning about storing a local
3228+
* variable's address in a long-lived variable.
3229+
*/
3230+
#ifdef HAVE__BUILTIN_FRAME_ADDRESS
3231+
stack_base_ptr = __builtin_frame_address(0);
3232+
#else
32243233
stack_base_ptr = &stack_base;
3234+
#endif
32253235
#if defined(__ia64__) || defined(__ia64)
32263236
register_stack_base_ptr = ia64_get_bsp();
32273237
#endif

src/backend/utils/init/miscinit.c

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -274,6 +274,14 @@ InitPostmasterChild(void)
274274
{
275275
IsUnderPostmaster = true; /* we are a postmaster subprocess now */
276276

277+
/*
278+
* Set reference point for stack-depth checking. This might seem
279+
* redundant in !EXEC_BACKEND builds; but it's not because the postmaster
280+
* launches its children from signal handlers, so we might be running on
281+
* an alternative stack.
282+
*/
283+
(void) set_stack_base();
284+
277285
InitProcessGlobals();
278286

279287
/*

src/include/pg_config.h.in

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -757,6 +757,9 @@
757757
/* Define to 1 if your compiler understands __builtin_ctz. */
758758
#undef HAVE__BUILTIN_CTZ
759759

760+
/* Define to 1 if your compiler understands __builtin_frame_address. */
761+
#undef HAVE__BUILTIN_FRAME_ADDRESS
762+
760763
/* Define to 1 if your compiler understands __builtin_$op_overflow. */
761764
#undef HAVE__BUILTIN_OP_OVERFLOW
762765

0 commit comments

Comments
 (0)