Vittorio Romeo
Vittorio Romeo

Reputation: 93294

Narrowing conversion from `int` (constant expression) to `unsigned int` - MSVC vs gcc vs clang

constexpr int i = 100;
struct F { F(unsigned int){} };
int main() { F{i}; }

The snippet above:

Q: is MSVC wrong here?

live example on godbolt.org


int i = 100;
struct F { F(unsigned int){} };
int main() { F{i}; }

Q: is g++ wrong here? (i.e. should it produce an hard error?)

live example on godbolt.org

Upvotes: 9

Views: 3121

Answers (1)

Yakk - Adam Nevraumont
Yakk - Adam Nevraumont

Reputation: 275500

There is never a requirement that any C++ program produce a hard error. There are requirements to print diagnostics. The form of the diagnostic is unspecified by the standard: an old joke is that printing out a single space satisifies the diagnostic requirements of the standard. That would be a quality of implementation issue.

There are ill-formed programs upon which the standard places no restrictions on their behavior, and sometimes a mandatory diagnostic.

There are cases where a program is ill-formed and a diagnostic is required. One way to handle that is to produce a message saying it is an error, then do not generate any binary to run. Another way is to produce a message saying it is a warning, then produce a binary that can be run.

So, g++ is not wrong under the standard for merely printing out a warning.

The resulting program is technically all undefined behavior; g++ could format your hard drive when it runs without violating the standard. That would be considered a quality of implementation issue.

Shafik's answer here covers the first question. i is constant expression and its value fits the target type; there should be no warning or error about the narrowing conversion.

The C++ standard does not defend you against hostile compilers.

Reportedly, -pedantic-errors can be passed to g++ to have it generate hard errors instead of warnings when the standard mandates the resulting program would be ill-formed.

Upvotes: 4

Related Questions