Created on 2025-04-01.00:00:00 last changed 1 week ago
Possible resolution:
Add a new paragraph after 13.9.2 [temp.inst] paragraph 8 as follows:
The existence of a definition of a variable or function is considered to affect the semantics of the program if the variable or function is needed for constant evaluation by an expression (7.7 [expr.const]), even if constant evaluation of the expression is not required or if constant expression evaluation does not use the definition. [ Example: ... ]Similarly, the existence of a definition of a variable or function is considered to affect the semantics of the program in which an expression E appears if the instantiation changes the type of E, even if the variable or function is not odr-used (6.3 [basic.def.odr]). [ Example:
template<typename T> struct X { static inline int arr[] = {1, 2, T::error}; }; decltype(+X<int>::arr) r; // error: definition of X<int>::arr is instantiated, because its type changes from "array of unknown bound" to "array of 3 int"-- end example ]
(From submission #843.)
When a variable has an incomplete array type and a braceed initializer, the complete array type can be determined by instantiating a definition of the variable; see 13.9.2 [temp.inst] paragraph 4 and 13.9.2 [temp.inst] paragraph 7. The level of tracking differs between implementations.
// Case 1: Clang rejects because the type of `*p` changes // between redeclarations; Clang seems to be incorrect: // The array bound affects the semantics of the program. template<typename T> struct X { static inline int arr[] = {1, 2, 3}; }; // Clang does not instantiate a definition here. extern decltype(X<int>::arr) *p; // Clang does instantiate a definition here. int n = sizeof(X<int>::arr); decltype(X<int>::arr) *p; // Case 2: GCC, EDG, MSVC reject because they instantiate a definition // of `X<int>::arr` even though it's not odr-used and doesn't appear to // affect the semantics of the program. template<typename T> struct X { static inline int arr[] = {1, 2, T::error}; }; // The array bound here doesn't matter; array-to-pointer decay doesn't // care about it. decltype(+X<int>::arr) r;
| History | |||
|---|---|---|---|
| Date | User | Action | Args |
| 2026-02-24 22:24:11 | admin | set | messages: + msg8490 |
| 2025-04-01 00:00:00 | admin | create | |