Subject: Re: Debian 12 gcc warning

From: Bruce Momjian <[email-masked]>
Date: Tue, 29 Aug 2023 09:27:23 -0400

On Tue, Aug 29, 2023 at 10:26:27AM +0700, John Naylor wrote:
> 
> On Tue, Aug 29, 2023 at 6:56 AM David Rowley <[email-masked]> wrote:
> >
> > I'm just not sure if it's unable to figure out if at least nargs
> > elements is set or if it won't be happy until all 100 elements are
> > set.
> 
> It looks like the former, since I can silence it on gcc 13 / -O1 by doing:
> 
> /* keep compiler quiet */
> actual_arg_types[0] = InvalidOid;

Agreed, that fixes it for me too.  In fact, assigning to only element 99 or
200 also prevents the warning, and considering the array is defined for
100 elements, the fact is accepts 200 isn't a good thing.  Patch attached.

I think the question is whether we add this to silence a common compiler
but non-default optimization level.  It is the only such case in our
source code right now.

-- 
  Bruce Momjian  <[email-masked]>        https://momjian.us
  EDB                                      https://enterprisedb.com

  Only you can decide what is important to you.
diff --git a/src/backend/optimizer/util/clauses.c b/src/backend/optimizer/util/clauses.c
index da258968b8..f4a1d1049c 100644
--- a/src/backend/optimizer/util/clauses.c
+++ b/src/backend/optimizer/util/clauses.c
@@ -4284,6 +4284,10 @@ recheck_cast_function_args(List *args, Oid result_type,
 	if (list_length(args) > FUNC_MAX_ARGS)
 		elog(ERROR, "too many function arguments");
 	nargs = 0;
+
+	/* Silence gcc 12 compiler at -O1. */
+	actual_arg_types[0] = InvalidOid;
+
 	foreach(lc, args)
 	{
 		actual_arg_types[nargs++] = exprType((Node *) lfirst(lc));

---

From: Tom Lane <[email-masked]>
Date: Tue, 29 Aug 2023 10:18:36 -0400

> 100 elements, the fact is accepts 200 isn't a good thing.  Patch attached.

That seems like a pretty clear compiler bug, particularly since it just
appears in this one version.  Rather than contorting our code, I'd
suggest filing a gcc bug.

			regards, tom lane

---

From: Bruce Momjian <[email-masked]>
Date: Tue, 29 Aug 2023 22:52:06 -0400

> suggest filing a gcc bug.

I assume I have to create a test case to report this to the gcc team.  I
tried to create such a test case on gcc 12 but it doesn't generate the
warning.  Attached is my attempt.  Any ideas?  I assume we can't just
tell them to download our software and compile it.

---

From: Tom Lane <[email-masked]>
Date: Tue, 29 Aug 2023 23:30:06 -0400

> tell them to download our software and compile it.

IIRC, they'll accept preprocessed compiler input for the specific file;
you don't need to provide a complete source tree.  Per
https://gcc.gnu.org/bugs/

    Please include all of the following items, the first three of which can be obtained from the output of gcc -v:

    the exact version of GCC;
    the system type;
    the options given when GCC was configured/built;
    the complete command line that triggers the bug;
    the compiler output (error messages, warnings, etc.); and
    the preprocessed file (*.i*) that triggers the bug, generated by adding -save-temps to the complete compilation command, or, in the case of a bug report for the GNAT front end, a complete set of source files (see below).

Obviously, if you can trim the input it's good, but it doesn't
have to be a minimal reproducer.

			regards, tom lane

---

From: Bruce Momjian <[email-masked]>
Date: Wed, 30 Aug 2023 11:16:48 -0400

> have to be a minimal reproducer.

Bug submitted, thanks for th preprocessed file tip.

---

From: Bruce Momjian <[email-masked]>
Date: Wed, 30 Aug 2023 11:34:22 -0400

> Bug submitted, thanks for th preprocessed file tip.

Good news, I was able to prevent the bug by causing compiling of
clauses.c to use -O2 by adding this to src/Makefile.custom:

	clauses.o : CFLAGS+=-O2

Here is my submitted bug report:

	https://gcc.gnu.org/bugzilla/show_bug.cgi?id=111240

---

From: Bruce Momjian <[email-masked]>
Date: Wed, 6 Sep 2023 12:33:31 -0400

> 	https://gcc.gnu.org/bugzilla/show_bug.cgi?id=111240

I got this reply on the bug report:

	https://gcc.gnu.org/bugzilla/show_bug.cgi?id=111240#c5

	Richard Biener 2023-08-31 09:46:44 UTC
	
	Confirmed.
	
	rettype_58 = enforce_generic_type_consistency (&actual_arg_types, &declared_arg_types, 0, _56, 0);
	
	and we reach this on the args == 0 path where indeed actual_arg_types
	is uninitialized and our heuristic says that a const qualified pointer
	is an input and thus might be read.  So you get a maybe-uninitialized
	diagnostic at the call.
	
	GCC doesn't know that the 'nargs' argument relates to the array and
	that at most 'nargs' (zero here) arguments are inspected.
	
	So I think it works as designed, we have some duplicate bugreports
	complaining about this "heuristic".
	
	We are exposing this to ourselves by optimizing the args == 0 case
	(skipping the initialization loop and constant propagating the
	nargs argument).  Aka jump-threading.
	
I think we just have to assume this incorrect warning will be around for
a while.