Google Groups no longer supports new Usenet posts or subscriptions. Historical content remains viewable.
Dismiss

May a compiler check arguments for non-prototyped functions?

338 views
Skip to first unread message

Keith Thompson

unread,
Sep 8, 2012, 5:38:42 PM9/8/12
to
N1370 6.5.2.2p8, discussing function calls, says:

No other conversions are performed implicitly; in particular,
the number and types of arguments are not compared with those
of the parameters in a function definition that does not include
a function prototype declarator.

Taken literally, this implies that a compiler may not check whether the
arguments in a call match the parameters of a non-prototyped function,
regardless of what it does with the information.

For example:

#include <stdio.h>

int func(n)
int n;
{
return n + 1;
}

int main(void) {
printf("func(0.1) = %d\n", func(0.1));
return 0;
}

Clearly no diagnostic is required, and the implementation is not
required to convert the argument 0.1 from double to int.

But a strict reading of 6.5.2.2p8 (some might say an overly pedantic
reading) implies that a compiler may not even warn about the type
mismatch on the call, because it would have to compare "the number
and types of arguments" with "those of the parameters in a function
definition" in order to produce such a warning.

Suggestion: That paragraph should be reworded to remove the
prohibition on comparing arguments vs. parameters, while still
stating that any such comparison doesn't result in an implicit
conversion.

Off the top of my head:

No other conversions are performed implicitly; in particular,
the number and types of the parameters in a function definition
that does not include a function prototype declarator are
not considered.

It might be argued that the current wording is clear enough, and that
the introductory "No other conversions are performed implicitly;"
implies that the rest of the paragraph only in that context.
In my opinion, though, it could easily be read either way.

--
Keith Thompson (The_Other_Keith) ks...@mib.org <http://www.ghoti.net/~kst>
Will write code for food.
"We must do something. This is something. Therefore, we must do this."
-- Antony Jay and Jonathan Lynn, "Yes Minister"

John Nagle

unread,
Sep 28, 2012, 11:58:18 PM9/28/12
to
On 9/8/2012 2:38 PM, Keith Thompson wrote:
> N1370 6.5.2.2p8, discussing function calls, says:
>
> No other conversions are performed implicitly; in particular,
> the number and types of arguments are not compared with those
> of the parameters in a function definition that does not include
> a function prototype declarator.
>
> Taken literally, this implies that a compiler may not check whether the
> arguments in a call match the parameters of a non-prototyped function,
> regardless of what it does with the information.

Since an non-matching call leads to undefined behavior, the
implementation may detect and report the problem.

What the compiler can't do is convert, say, an int to a float
to make parameters match.

John Nagle

Keith Thompson

unread,
Sep 29, 2012, 12:52:50 AM9/29/12
to
John Nagle <na...@animats.com> writes:
> On 9/8/2012 2:38 PM, Keith Thompson wrote:
>> N1370 6.5.2.2p8, discussing function calls, says:
>>
>> No other conversions are performed implicitly; in particular,
>> the number and types of arguments are not compared with those
>> of the parameters in a function definition that does not include
>> a function prototype declarator.
>>
>> Taken literally, this implies that a compiler may not check whether the
>> arguments in a call match the parameters of a non-prototyped function,
>> regardless of what it does with the information.
>
> Since an non-matching call leads to undefined behavior, the
> implementation may detect and report the problem.

Which contradicts the literal wording of the standard. A compiler
would have to compare the arguments with the parameters in order
to detect and report such a problem.

> What the compiler can't do is convert, say, an int to a float
> to make parameters match.

So the behavior is undefined except that it can't do a specific
conversion? How do you reach that conclusion. I find it difficult
to believe that that was the intent.

Richard Damon

unread,
Sep 29, 2012, 12:55:13 AM9/29/12
to
Since undefined behavior has been invoked at this point, the compiler is
free to convert the int to a float.

What the compiler is prohibited from doing is to notice the type
discrepancy and consider it a constraint violation and then decide to
not translate the program. Any diagnostic created needs to be limited to
a "warning" (not a Standard term, but common practice), and not an
"error" as the code is still syntactically valid, undefined behavior is
only invoked in this case at execution time when the call is actually
made.

Harald van Dijk

unread,
Sep 29, 2012, 7:02:07 AM9/29/12
to
On Saturday, September 8, 2012 11:38:44 PM UTC+2, Keith Thompson wrote:
> N1370 6.5.2.2p8, discussing function calls, says:
>
> No other conversions are performed implicitly; in particular,
> the number and types of arguments are not compared with those
> of the parameters in a function definition that does not include
> a function prototype declarator.
>
> Taken literally, this implies that a compiler may not check whether the
> arguments in a call match the parameters of a non-prototyped function,
> regardless of what it does with the information.
>
> For example:
>
> #include <stdio.h>
> int func(n)
> int n;
> {
> return n + 1;
> }
>
> int main(void) {
> printf("func(0.1) = %d\n", func(0.1));
> return 0;
> }
>
> Clearly no diagnostic is required, and the implementation is not
> required to convert the argument 0.1 from double to int.
>
> But a strict reading of 6.5.2.2p8 (some might say an overly pedantic
> reading) implies that a compiler may not even warn about the type
> mismatch on the call, because it would have to compare "the number
> and types of arguments" with "those of the parameters in a function
> definition" in order to produce such a warning.

I'll go with overly pedantic :) Even if the text explicitly stated a compiler is prohibited from checking argument types for diagnostic purposes, the as-if rule would /still/ allow a compiler to completely ignore that and warn anyway, would it not? After all, the compiler is indistinguishable from one that has a hardcoded but undocumented built-in list of programs for which an extra warning should be generated, so the warning /could/ have been generated without actually checking the argument types. (I am aware that the as-if rule generally applies to runtime behaviour, but 5.1.2.3 "the least requirements on a conforming implementation are" does not include anything about translation time behaviour, so I believe the as-if rule is technically even stronger here.)

Tim Rentsch

unread,
Dec 21, 2012, 10:58:06 AM12/21/12
to
John Nagle <na...@animats.com> writes:

> On 9/8/2012 2:38 PM, Keith Thompson wrote:
>> N1370 6.5.2.2p8, discussing function calls, says:
>>
>> No other conversions are performed implicitly; in particular,
>> the number and types of arguments are not compared with those
>> of the parameters in a function definition that does not include
>> a function prototype declarator.
>>
>> Taken literally, this implies that a compiler may not check whether the
>> arguments in a call match the parameters of a non-prototyped function,
>> regardless of what it does with the information.
>
> Since an non-matching call leads to undefined behavior, the
> implementation may detect and report the problem. [snip unrelated]

Any potential undefined behavior occurs only during execution.
The decision about whether to issue a diagnostic occurs during
translation, and therefore cannot use the later UB as an excuse
not to observe other requirements.
0 new messages