C2Y: issue log

Issue Summary Status
1094 Missing [[unsequenced]] in <stdbit.h> Open
1096 fopen mode string issues Open
1097 Incomplete internal linkage tentative definitions completed in inner scope Open
1098 Source files not ending with newline Open
1099 UCNs from token concatenation Open
1100 <math.h> overflow in non-default rounding modes Open
1101 Static assertions in expressions in for loops Open

Issue 1094: Missing [[unsequenced]] in <stdbit.h>

Authors: Joseph Myers
Date: 2026-08-26
Submitted against: C2Y (N3886 draft)
Status: Open

When N3367 (More Modern Bit Utilities) was adopted for C2Y, it was without [[unsequenced]] attributes, since those in the paper were neither complete nor all correct, and with the expectation of a separate paper later to add such attributes. They should be added to all the new functions except for the stdc_store8_* functions.

Suggested correction

Add the [[unsequenced]] attributes immediately before the final semicolon of all <stdbit.h> functions (including generic functions) in 7.18.17 (Rotate Left), 7.18.18 (Rotate Right), 7.18.19 (8-bit Memory Reversal), 7.18.20 (Exact-width 8-bit Memory Reversal), and 7.18.21 (Endian-Aware 8-bit Load).



Issue 1096: fopen mode string issues

Authors: Joseph Myers
Date: 2026-08-27
Submitted against: C2Y (N3886 draft)
Status: Open

Reflector message 26283 notes various issues with the specification for fopen mode strings that remain after the integration of N3247 (and the subsequent N3275 for fopen_s).

  1. The wording for '+' needs updating to reflect that it might not be the second or third character any more with relaxed ordering; it could be any character after the first. This could probably be fixed editorially by saying "a" in place of "the second or third".
  2. The footnote "If the string begins with one of the listed mode sequences, the implementation can choose to ignore the remaining characters, or it can use them to select different kinds of a file (some of which can potentially not conform to the properties in 7.24.2)." only really made sense as is when there was a full list of possible mode sequences; now there's a mode character followed by other characters in any order, it needs to be rephrased so it no longer talks about "one of the listed mode sequences". Also, we should consider carefully where this footnote should go; is the current paragraph (which starts talking about the first character in the argument, leaving other characters for later) really the best place still?
  3. Previously there was explicit undefined behavior for any string not in the given list. Now, there's only explicit undefined behavior if the first character isn't in the list; the normative wording says nothing about what happens if any subsequent character is not one for which semantics are defined. Maybe it's implicitly undefined where it says "can contain any of the following characters in any order", if some other character is present, but being explicit is generally better. (This is an example of "undefined behavior as an extension point", where implementations might give other meanings to strings with other characters; cf. the footnote discussed above. A request to make it implementation-defined in C23 CD1 comment GB-210 was rejected (no consensus 4/4/5) with "David Banham asked to bring this suggestion up for C2Y", i.e. a paper making an extension point might be appropriate to consider. This could not be implementation-defined behavior in the sense of enumerated alternatives, however, only kind of implementation-documented but unbounded behavior discussed in N3863.)
  4. It has been suggested to me that the wording about 'p' is inadequate, because "cannot be accessed by other means" would seem to exclude all the suggested implementation strategies; O_TMPFILE or a suid helper doesn't prevent access via /proc/self/fd/, for example, or by direct privileged access to the underlying device. It may be that this is a case where the normative wording can only be understood to refer to mechanisms within the scope of the standard, however, and as with memset_explicit not all the intent about what is or is not an appropriate implementation strategy can be expressed within the concepts usable in normative wording in terms of the abstract machine. The normative wording should probably be reworded to avoid saying things that cannot be implemented, and further matters of intent moved to Recommended Practice. Unlike the first three issues, the problematic wording appears for fopen_s as well as for fopen. I tend to think that it would be best for the fopen_s specification to say as little as possible about the semantics of 'x' and 'p', deferring instead to the fopen specification as far as possible.


Issue 1097: Incomplete internal linkage tentative definitions completed in inner scope

Authors: Joseph Myers
Date: 2026-08-27
Submitted against: C2Y (N3886 draft)
Status: Open

As noted in reflector message 34118, the adoption of N3347, with wording taken from reflector message 26758, left an ambiguously worded constraint. 6.9.3 (External object definitions) paragraph 1 says:

If the declaration of an identifier for an object is a tentative definition with incomplete type and internal linkage, the type of the object shall be completed before the end of the translation unit.

Suppose the type is completed in an inner scope:

static int a[];
void f() { extern int a[1]; }

Is this valid, because the type gets completed in an inner scope before the end of the translation unit, or invalid, because the type at the end of the translation unit is incomplete even though the type inside f at the end of that function is complete?



Issue 1098: Source files not ending with newline

Authors: Joseph Myers
Date: 2026-09-01
Submitted against: C2Y (N3886 draft)
Status: Open

As noted in reflector message 33995, when we accepted N3411, allowing source files without a final newline, we did not make any corresponding change to the syntax for many preprocessing directives, which includes new-line, as does that for text-line, so leaving syntax violations for source files without the final newline character, when the intent was to allow such file as if the final newline were added. It was also said when we accepted N3478, making partial comments at the end of a file into a constraint violation, that we should allow a // comment on the final line of a file without needing trailing newline.

In reflector message 34017, Corentin Jabot suggested following the wording used by C++. This would allow a source file with no final newline without allowing the case where the source file ends with a backslash (and no following newline) to act as if line splicing occurs. It would both resolve the issues introduced by the integration of N3411, and allow a // comment on the final line of a file without a trailing newline to be handled as such rather than being a constraint violation.

Suggested correction

At the end of translation phase 2 in 5.2.1.2 (Translation phases), add:

  1. Each instance of a backslash character (\) immediately followed by a new-line character is deleted, splicing physical source lines to form logical source lines. Only the last backslash on any physical source line shall be eligible for being part of such a splice. A source file that is not empty and that (after splicing) does not end in a new-line character is processed as if an additional new-line character were appended to the file.


Issue 1099: UCNs from token concatenation

Authors: Joseph Myers
Date: 2026-09-01
Submitted against: C2Y (N3886 draft)
Status: Open

In reflector message 29430, Corentin Jabot noted that the adoption of N3418, disallowing producing a UCN by token concatenation, was the opposite of existing practice and that C++ requires this to be accepted, so the change diverges C from C++ without good reason.

Suggested correction

In 6.10.5.4 (The ## operator), delete the second Constraint.

A character sequence that matches the syntax of a universal character name shall not be produced by token concatenation.



Issue 1100: <math.h> overflow in non-default rounding modes

Authors: Joseph Myers
Date: 2026-09-01
Submitted against: C2Y (N3886 draft)
Status: Open

N3737 made changes to <math.h> error handling that were described as being clarifications.

Those changes added one sentence that is very unclear, with problematic effects on another changed sentence. The unclear sentence is

Range errors in non-default rounding modes are implementation-defined.

in 7.12.2 paragraph 5. This does not say anything about what aspects of range errors are implementation-defined or what the options available to implementations are: whether it's implementation-defined when such errors occur, or what value functions return on such errors, or what exceptions are raised, or what value errno is set to, or any other aspect of how the abstract machine behaves on error. It does not say whether any other sentence describing range errors is still applicable in the case of non-default rounding modes, although normally such sentences would still apply unless specifically excluded. (The case of the value returned is excluded in text referring to HUGE_VAL returned on overflow, which only discusses the return value when "default rounding is in effect".)

Consider the case of a range error for overflow that is specified to "occur", rather than as "may occur", in a non-default rounding mode, for an implementation where math_errhandling & MATH_ERRNO is nonzero. The current wording in 7.12.2 paragraph 7 says:

If a range error occurs because of floating-point overflow and the integer expression math_errhandling & MATH_ERRNO is nonzero, the integer expression errno acquires the value ERANGE.

Previously, this only applied if "default rounding is in effect". Does the implementation-defined behavior act to change all "occur" into "may occur" in a non-default rounding mode, or to make it implementation-defined whether errno is set even when the error occurs? Or does this sentence about overflow now require errno to be set where it was not previously required to be set, with the implementation-defined behavior only changing some smaller aspect that is genuinely unspecified by other text in the standard, such as the precise overflow threshold or the returned value (both of which do depend on the rounding mode in IEC 60559 floating point)?

If errno is now required to be set for some overflows in non-default rounding modes (where it was clearly not previously required to be set), that is problematic because such overflows cannot generally be detected by the implementation from the value it computes, unlike in round-to-nearest, since the largest finite value of the appropriate sign can occur in both overflowing and non-overflowing cases in some rounding modes.



Issue 1101: Static assertions in expressions in for loops

Authors: Joseph Myers
Date: 2026-09-01
Submitted against: C2Y (N3886 draft)
Status: Open

As noted in reflector message 34193, the addition of static assertions in expressions from N3715 included syntactic disambiguation for block items, but not for the first clause of a for statement. (As with that for block items, this doesn't affect the final semantics of the static assertion, just which sequence of syntax productions it goes through. There is no such syntactic ambiguity in the selection header of if or switch.)

Suggested correction

In 6.8.6.4 (The for statement), amend the second paragraph.

Both clause-1 and expression-3 can be omitted. If clause-1 is a static assertion, it is interpreted as a static_assert declaration. An omitted expression-2 is replaced by a nonzero constant.