Skip to content

Don't use C23 constexpr keyword#19

Open
thesamesam wants to merge 1 commit intofanf2:masterfrom
thesamesam:c23
Open

Don't use C23 constexpr keyword#19
thesamesam wants to merge 1 commit intofanf2:masterfrom
thesamesam:c23

Conversation

@thesamesam
Copy link
Copy Markdown

This fixes building with upcoming GCC 15 which defaults to -std=gnu23.

This fixes building with upcoming GCC 15 which defaults to -std=gnu23.
@musicinmybrain
Copy link
Copy Markdown

I’ve just taken over maintainership of the unifdef package in Fedora. I’m working on modernizing and improving the downstream packaging, and on updating to the latest upstream release; obviously, the downstream package was quite out of date!

This PR works well for me, particularly in combination with #14, but I’m finding that in Fedora 42 and later, which have GCC 15, I encounter some regressions in the tests:

+ /usr/bin/make -O -j16 V=1 VERBOSE=1 test
scripts/reversion.sh
scripts/runtests.sh tests
........................................................................................
FAILED: whitespace-1.out: unifdef -DFOO whitespace.c
--- whitespace-1.expout 2020-02-14 11:58:52.000000000 -0500
+++ whitespace-1.out    2025-05-08 09:34:23.782122075 -0400
@@ -1 +1,6 @@
 foo
+                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                               //spong
+
+#ifdef BAR
+bar
+#endif

FAILED: whitespace-1.err: unifdef -DFOO whitespace.c
--- whitespace-1.experr 2020-02-14 11:58:52.000000000 -0500
+++ whitespace-1.err    2025-05-08 09:34:23.783122090 -0400
@@ -1,2 +0,0 @@
-unifdef: whitespace.c: 4: Obfuscated preprocessor control line (#if line 1 depth 1)
-unifdef: Output may be truncated

FAILED: whitespace-1.rc: unifdef -DFOO whitespace.c
--- whitespace-1.exprc  2020-02-14 11:58:52.000000000 -0500
+++ whitespace-1.rc     2025-05-08 09:34:23.782122075 -0400
@@ -1 +1 @@
-2
+1
.
FAILED: whitespace-2.out: unifdef -DBAR whitespace.c
--- whitespace-2.expout 2020-02-14 11:58:52.000000000 -0500
+++ whitespace-2.out    2025-05-08 09:34:23.812122510 -0400
@@ -1,5 +1,6 @@
 #ifdef FOO
 foo
-#endif                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                        //spong
+#endif                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                 
+                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                               //spong

 bar
.
make: *** [Makefile:21: test] Error 1

(There are a couple of spots in the whitespace-2.expout/whitespace-2.out diff where a lot of vertical whitespace appears in my terminal, but not when I copy and paste it above.)

I’m not prepared to dig into this deeply, so for now, I’m planning to just skip these two tests and report the problem by email. I am curious whether you encountered the same problem and whether you chose to investigate it.

@thesamesam
Copy link
Copy Markdown
Author

thesamesam commented May 8, 2025

Let me have a look. It might be a good task for one of my mentees as well.

@thesamesam
Copy link
Copy Markdown
Author

thesamesam commented May 10, 2025

https://gcc.gnu.org/PR120205 (EDIT: see #19 (comment))

@musicinmybrain
Copy link
Copy Markdown

https://gcc.gnu.org/PR120205

Thank you for investigating this and distilling it into a viable upstream bug report!

gentoo-bot pushed a commit to gentoo/gentoo that referenced this pull request May 10, 2025
The unifdef testsuite has been failing sometimes for years with
_FORTIFY_SOURCE in a non-obvious way, where glibc's fgets will return
\0 w/ n=1.

I'd found marxin's PR for this years ago and apparently completely forgot
about it (nor did I backport the patch into Gentoo at the time, as
I didn't maintain it, and I was fairly new then).

Backport marxin's patch from 2022 accordingly. Thanks to Ben Beasley
poking me on the upstream PR (19) which made me look at all of this
again.

Bug: https://gcc.gnu.org/PR120205
Bug: fanf2/unifdef#15
Bug: fanf2/unifdef#19
Closes: https://bugs.gentoo.org/836698
Signed-off-by: Sam James <sam@gentoo.org>
@thesamesam
Copy link
Copy Markdown
Author

Man, what a mess. Sorry for the runaround. I'm still not maintaining unifdef downstream but it's now marked as maintainer-needed (orphaned) so only started paying any attention to it recently.

TL;DR: We need #15 and fgets has interesting behaviour with _FORTIFY_SOURCE.

@musicinmybrain
Copy link
Copy Markdown

TL;DR: We need #15 and fgets has interesting behaviour with _FORTIFY_SOURCE.

I can confirm that #15 works for me. I had dug through the open PR’s, but I hadn’t found that one. Thanks again.

@atsampson
Copy link
Copy Markdown

I've run into this as well, packaging unifdef with GCC 15.1.0.

I'm not convinced that the change in #15 is right - it modifies the expected output for the whitespace tests so that they silently split a long line in two without emitting a diagnostic, which isn't correct behaviour. I think it's probable that there is a GCC bug here, since adding _FORTIFY_SOURCE shouldn't change behaviour unless the code had UB to start with (which I don't think is the case here, and ASan/UBSan doesn't find anything).

In the long run, it may be easiest to get rid of the line length limitation - e.g. use getline rather than fgets, and make tline a pointer (using realloc if necessary to ensure there's still EDITSLOP space after the line).

@thesamesam
Copy link
Copy Markdown
Author

thesamesam commented Jul 6, 2025

since adding _FORTIFY_SOURCE shouldn't change behaviour unless the code had UB to start with (which I don't think is the case here, and ASan/UBSan doesn't find anything

I don't think UBsan knows about POSIX constraints here (or indeed often behaviour of C standard library functions unless they can be expressed via some attribute we already have, like nonnull) and the argument is that the behaviour relied upon from fgets is unspecified, but I'm not sure on that last part.

I think it's probable that there is a GCC bug here

The relevant code is in glibc.

In libio/bits/stdio.h:

__fortify_function __wur __fortified_attr_access (__write_only__, 1, 2)
__nonnull ((3)) __attribute_overloadable__ char *
fgets (__fortify_clang_overload_arg (char *, __restrict, __s), int __n,
       FILE *__restrict __stream)
     __fortify_clang_warning (__fortify_clang_bos_static_lt (__n, __s) && __n > 0,
                              "fgets called with bigger size than length of "
                              "destination buffer")
{
  size_t __sz = __glibc_objsize (__s);
  if (__glibc_safe_or_unknown_len (__n, sizeof (char), __sz))
    return __fgets_alias (__s, __n, __stream);
#if !__fortify_use_clang
  if (__glibc_unsafe_len (__n, sizeof (char), __sz))
    return __fgets_chk_warn (__s, __sz, __n, __stream);
#endif
  return __fgets_chk (__s, __sz, __n, __stream);
}

__glibc_objsize can only do something with _FORTIFY_SOURCE.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants