What is the C++ compiler required to do with ill-formed programs according to the Standard?
Asked Answered
R

4

29

C++03 Standard defines well-formed program (1.3.14 [defns.well.formed]) as

a C++ program constructed according to the syntax rules, diagnosable semantic rules, and the One Definition Rule (3.2)

It further defines an ill-formed program (1.3.4 [defns.ill.formed]) as

input to a C++ implementation that is not a well-formed program (1.3.14)

and the Standard is full of statements such as "if X then the program is ill-formed" for example (2.13.1/3):

A program is ill-formed if one of its translation units contains an integer literal that cannot be represented by any of the allowed types.

Yet I haven't found what the C++ implementation is required to do with ill-formed programs.

Suppose I have an ill-formed program. Now what?

Is the C++ implementation required to do something specific when it encounters an ill-formed program or is the C++ implementation behavior just undefined?

Recusancy answered 4/4, 2013 at 7:48 Comment(0)
P
18

Is the C++ implementation required to do something specific when it encounters an ill-formed program or is the C++ implementation behavior just undefined?

If the Standard does not specify otherwise, an implementation should emit a diagnostic message (error or warning). However, for some violations the Standard explicitly specifies that no diagnostic is required. In this case, the program is ill-formed, but implementations are not required to tell the user - usually, because doing so in the general case would be too difficult.

Concerning the One Definition Rule, for example, see Paragraph 3.2/4 of the C++11 Standard:

Every program shall contain exactly one definition of every non-inline function or variable that is odr-used in that program; no diagnostic required.

Regarding the requirements on implementations when encountering a violation of a rule, Paragraph 1.4/2 specifies:

[...]

— If a program contains no violations of the rules in this International Standard, a conforming implementation shall, within its resource limits, accept and correctly execute that program.

If a program contains a violation of any diagnosable rule or an occurrence of a construct described in this Standard as “conditionally-supported” when the implementation does not support that construct, a conforming implementation shall issue at least one diagnostic message.

— If a program contains a violation of a rule for which no diagnostic is required, this International Standard places no requirement on implementations with respect to that program.

Also relevant is Paragraph 1.4/1, which explains what is meant by "diagnosable rules" in the Paragraph quoted above:

The set of diagnosable rules consists of all syntactic and semantic rules in this International Standard except for those rules containing an explicit notation that “no diagnostic is required” or which are described as resulting in “undefined behavior.”

So to sum it up: if an ill-formed program contains a diagnosable violation for which the Standard does not explicitly specify "no diagnostic required", conforming implementations should emit a diagnostic.

Platyhelminth answered 4/4, 2013 at 7:56 Comment(16)
As it happens, there is only one non-diagnosable rule that renders a program ill-formed: the One Definition Rule. At least, that's the case for C++03, I haven't checked C++11. The definition is 1.3.14. Breaking the the other rules that say "no diagnosis required" results in a well-formed program with undefined behavior.Semiskilled
@SteveJessop: I would call your attention to the quote in Luchian's answer, where it is required that all well-formed programs have specific behavior. That implies that all of the rules that make a designation of "undefined behavior" are in fact saying that such a program is not well-formed. Is there a distinction between "not well-formed" and "ill-formed"?Envelopment
@BenVoigt: referring to C++03, "ill-formed" means "not well-formed", and "well-formed" means "obeying the syntax rules, the diagnosable semantic rules and the ODR". Since not all ODR-violations are diagnosable (specifically those involving multiple or inconsistent definitions in different TUs), this would appear to be a contradiction. I now suspect the answer is that the definition of well-formed means that if there's a violation within a single TU (which is diagnosable) then it's ill-formed, and that I missed some context in interpreting it. Thanks for drawing my attention to that :-)Semiskilled
You say: "If the Standard does not specify otherwise, an implementation should emit an error", but it does only apply when a program violates a rule, but the sharptooth's question is about a rule with the following structure: "Rule R: If a program has the property P, it's a ill-formed program". If the compiler finds a program satisfying P, does it violate the rule R?Satem
@Peregring-lk: I'm not sure I understand your point, but yes, if a program satisfies P, then that program violates R. However, for a program violating R, the compiler is only required to emit a diagnostic if R does not specify that "no diagnostic is required". If that's not specified, the compiler shall emit a diagnostic.Platyhelminth
@AndyProwl I don't agree with you: a->b, a ⊢ ¬(a->b). Are you sure? (R ≡ a->b; a ≡ "property P"; b ≡ "the program is ill-formed") If a->b ∧ a, the only thing you can say is b and no more.Satem
@Peregring-lk: If I say "no yellow car shall exist" and that's my rule R (i.e. "if a car has property IsYellow then that car is illegal") and it turns out there is one yellow car out there (satisfying the IsYellow property), then that car violates my rule R. What's wrong with this reasoning?Platyhelminth
@AndyProwl "If a car has property IsYellow then that car is illegal" is your rule R, but "no yellow car shall exist" doesn't, and both are not equivalent sentences. If the first sentence is true, the second sentence is violated, that's true and I agree with you, but, does it exist such a rule in the C++ standard?Satem
@Peregring-lk: "No yellow car shall exist" is a consequence of the existence of a rule saying "A yellow card should not exist". What would be the point of a Standard that specifies 1300 pages of rules and allow valid programs to violate them? If a program contains a violation of any diagnosable rule [...] a conforming implementation shall issue at least one diagnostic message.Platyhelminth
@AndyProwl Perhaps you're right, but I don't see it completely clear. If this main rule would be something like: "If a program is a ill-formed one, a conforming implementation shall issue at least one diagnostic message", there would be no problems, but that sentence is expressed in the Standard in terms of "rule violation" and doesn't in terms of "ill-formedness", and a program violating P doesn't violate R. It does only express a property about a program: that it is ill-formed.Satem
Ok so, I've found a reasoning which agrees with your point. See my answer.Satem
@stevejessop A template function for which there are no valid specializations is also "ill-formed, no diagnostic required".Hereinto
Can you clarify the term error, usually I think of the term error to mean that translation will fail versus a warning which will allow translation to continue.Sputum
@Shafik: I edited the answer, indeed the term 'error' was not very accurate. The Standard requires a "diagnostic" to be emitted, which could be either an error or a warning.Platyhelminth
Thank you, so I was trying to nail this down, is an error for ill-formed code purely a quality of implementation issue?Sputum
@Shafik: If the code is ill-formed, the compiler needs to emit a message. Whether this message should be an error or a warning, that's at the implementation's discretion, but the implementation cannot stay entirely silent about it (unless the code is ill-formed because it violates a "no diagnostics required" rule, as written in the answer).Platyhelminth
B
4

Quoting [intro.compliance]§2:

  • If a program contains no violations of the rules in this International Standard, a conforming implementation shall, within its resource limits, accept and correctly execute that program.

  • If a program contains a violation of any diagnosable rule or an occurrence of a construct described in this Standard as “conditionally-supported” when the implementation does not support that construct, a conforming implementation shall issue at least one diagnostic message.

  • If a program contains a violation of a rule for which no diagnostic is required, this International Standard places no requirement on implementations with respect to that program.

I haven't found any other relevant passages in the standard. If we combine this with [defns.undefined]:

undefined behavior

behavior for which this International Standard imposes no requirements

[ Note: Undefined behavior may be expected when this International Standard omits any explicit definition of behavior or when a program uses an erroneous construct or erroneous data. Permissible undefined behavior ranges from ignoring the situation completely with unpredictable results, to behaving during translation or program execution in a documented manner characteristic of the environment (with or without the issuance of a diagnostic message), to terminating a translation or execution (with the issuance of a diagnostic message). Many erroneous program constructs do not engender undefined behavior; they are required to be diagnosed. -end note ]

I'd say we arrive at "issue a diagnostic message and further the behaviour is undefined," because the standard doesn't say anything more about it.

Beefsteak answered 4/4, 2013 at 7:55 Comment(8)
Okay, it "shall issue at least one diagnostic message" and then what should it do?Recusancy
@Recusancy Whatever it wants. The standard "omits any explicit definition of behavior" in this case, so it is undefined behavior. Conformance does not guarantee usability: a compiler which had a single error message (e.g. "?"), and reformatted your hard disk any time it encountered an error would be conforming. I doubt it would find wide acceptance, however.)Fusspot
@JamesKanze +1. I love people coming up with weird examples of UB.Beefsteak
@Angew The standard specifies "undefined behavior" for a variety of reasons. One, of course, is that it would otherwise require runtime checks (with corresponding cost), and another is that it would be too difficult to verify. Two others, however, are to allow the compiler to specify something that is reasonable in its environment (in cases where there is no "portable" or generic reasonable), or to provide extensions. (The usual "hook" for extensions is the fact that two successive underscores in a symbol is undefined behavior.)Fusspot
@JamesKanze Double underscores are "reserved to the implementation for any use". I don't think that's UB.Beefsteak
@Angew Then it has changed. But as I read it (§2.11/3): "some identifiers are reserved for use by C++ implementations and standard libraries (17.6.4.3.2) and shall not be used otherwise; no diagnostic is required." "no diagnostic is required" is a synonym for "undefined behavior".Fusspot
@JamesKanze OK, I was actually quoting (17.6.4.3.2). You're right, (2.11) does make it UB to misuse them.Beefsteak
@AngewisnolongerproudofSO: Suppose the Standard were to say that implementations may use identifiers starting with two underscores for any purpose they see fit, with or without documenting them (compiler-supplied header files will often make use of such identifiers for a variety of purposes without documenting them if the headers are expected to be replaced when a compiler is updated). Is there anything a conforming implementation could do given that definition which it couldn't do if use of such underscores was simply regarded as UB?Alleyn
S
3

(First of all, sorry for my English)

The Standard, in §1.4.2 says:

If a program contains a violation of any diagnosable rule [...] a conforming implementation shall issue at least one diagnostic message.

The definition of a ill-formed program is "a program that is not well formed" (§1.3.9), and a well-formed program is (§1.3.26):

C++ program constructed according to the syntax rules, diagnosable semantic rules, and the One Definition Rule

So, a ill-formed program does implicitly violate "some" rule. If a rule R has the following structure:

If a program has property P, it is an ill-formed program.

When a program has such property P, it does implicitly violate a rule (by definition of an ill-formed program), although it isn't clear which rule is the one which are being violated, since R itself doesn't (from a strictly logical point of view).

Satem answered 5/2, 2014 at 23:40 Comment(0)
I
1

The only relevant quote I could find says that an implementation is required to diagnose an ill-formed program, but it can finish compiling it:

1.4 Implementation compliance [intro.compliance]

8) A conforming implementation may have extensions (including additional library functions), provided they do not alter the behavior of any well-formed program. Implementations are required to diagnose programs that use such extensions that are ill-formed according to this International Standard. Having done so, however, they can compile and execute such programs.

Islander answered 4/4, 2013 at 7:53 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.