stdarg.h

The file stdarg.h defines the type va_list and the va_arg(), va_end(), and va_start() macros. The va_list type implements a pointer to one argument of a open parameter list. The va_start() macro initializes a variable of type va_list to point to the first open parameter, given the last explicit parameter and its type as arguments. The va_arg() macro returns one open parameter, given its type and also makes the va_list argument pointing to the next parameter. The va_end() macro finally releases the actual pointer. For all implementations, the va_end() macro does nothing because va_list is implemented as an elementary data type and therefore it must not be released. The va_start() and the va_arg() macros have a type parameter, which is accessed only with sizeof(). So type, but also variables can be used. See the following listing for an example using stdarg.h.

Listing: Example using stdarg.h


char sum(long p, ...) {

  char res=0;

  va_list list= va_start()(p, long);

  res= va_arg(list, int); // (*)

  va_end(list);

  return res; 

}

void main(void) {

  char c = 2;

  if (f(10L, c) != 2) Error();

}

In the line (*) va_arg must be called with int, not with char. Because of the default argument-promotion rules of C, for integral types at least an int is passed and for floating types at least a double is passed. In other words, the result of using va_arg(..., char) or va_arg(..., short) is undefined in C. Be especially careful when using variables instead of types for va_arg(). In the example above, res= va_arg(list, res) is not correct unless res has the type int and not char.