Default argument promotions in C function calls

Solution 1:

Upvoted AProgrammer's answer—those are the real goods.

For those of you who are wondering why things are this way: in the dark ages before 1988, there was no such thing as a function prototype in classic "K&R" C, and the default argument promotions were instituted because (a) there were essentially "free", as it costs no more to put a byte in a register than to put a word in a register, and (b) to cut down on potential errors in parameter passing. That second reason never quite cut it, which was why the introduction of function prototypes in ANSI C was the single most important change ever in the C language.

As to when default promotions kick in: default argument promotions are used exactly when the expected type of the argument is unknown, which is to say when there's no prototype or when the argument is variadic.

Solution 2:

  • (Non variadic) parameters to functions with a prototype are converted to the corresponding type, which can be char, short, float.

  • Parameters to functions without prototype and variadic parameters are subject to default argument promotions.

If you define a function with a prototype and use it without the prototype or vise versa and it has parameters of type char, short or float, you'll probably have a problem at run-time. You'll have the same kind of problems with variadic functions if the promoted type doesn't match what is used when reading the argument list.

Example 1: problem when defining a function with a prototype and using it without.

definition.c

void f(char c)
{
   printf("%c", c);
}

use.c

void f();

int main()
{
   f('x');
}

can fail because an int will be passed and the function expect a char.

Example 2: problem when defining a function without a prototype and using it with one.

definition.c

void f(c)
   char c;
{
   printf("%c", c);
}

(This is kind of definition is very old fashioned)

use.c

void f(char c);

int main()
{
   f('x');
}

can fail because an int is expected but a char will be passed.

Note: you'll remark that all functions from the standard library have types which result from default promotions. So they didn't cause problem during the transition when prototypes were added.