HPlogo HP C/HP-UX Reference Manual: Workstations and Servers > Chapter 10 HP C/HP-UX Implementation Topics

The varargs Macros

» 

Technical documentation

Complete book in PDF

 » Table of Contents

 » Index

The varargs macros allow accessing arguments of functions where the number and types of the arguments can vary from call to call.

NOTE: The <varargs.h> header has been superseded by the standard header <stdarg.h>, which provides all the functionality of the varargs macros. The <varargs.h> header is retained for compatibility with pre-ANSI compilers and earlier releases of HP C/HP-UX.

To use varargs, a program must include the header <varargs.h>. A function that expects a variable number of arguments must declare the first variable argument as va_alist in the function declaration. The macro va_dcl must be used in the parameter declaration.

A local variable should be declared of type va_list. This variable is used to point to the next argument in the variable argument list.

The va_start macro is used to initialize the argument pointer to the initial variable argument.

Each variable argument is accessed by calling the va_arg macro. This macro returns the value of the next argument, assuming it is of the specified type, and updates the argument pointer to point to the next argument.

The va_end macro is provided for consistency with other implementations; it performs no function on the HP 9000 Series 800 computers. The following example demonstrates the use of the <varargs.h> header:

Example

 #include <varargs.h>
#include <stdio.h>

enum arglisttype {NO_VAR_LIST, VAR_LIST_PRESENT};
enum argtype {END_OF_LIST, CHAR, DOUB, INT, PINT};

int foo (va_alist)
va_dcl /* Note: no semicolon */
{
va_list ap;
int a1;
enum arglisttype a2;

enum argtype ptype;
int i, *p;
char c;
double d;

/* Initialize the varargs mechanism */
va_start(ap);

/* Get the first argument, and arg list flag */
a1 = va_arg (ap, int);
a2 = va_arg (ap, enum arglisttype);

printf ("arg count = %d\n", a1);

if (a2 == VAR_LIST_PRESENT) {
/* pick up all the arguments */
do {
/* get the type of the argument */
ptype = va_arg (ap, enum argtype);

/* retrieve the argument based on the type */
switch (ptype) {
case CHAR: c = va_arg (ap, char);
printf ("char = %c\n", c);
break;

case DOUB: d = va_arg (ap, double);
printf ("double = %f\n", d);
break;

case PINT: p = va_arg (ap, int *);
printf ("pointer = %x\n", p);
break;

case INT : i = va_arg (ap, int);
printf ("int = %d\n", i);
break;

case END_OF_LIST :
break;

default: printf ("bad argument type %d\n", ptype);
ptype = END_OF_LIST; /* to break loop */
break;
} /* switch */
} while (ptype != END_OF_LIST);
}

/* Clean up */
va_end (ap);
}

main()
{
int x = 99;

foo (1, NO_VAR_LIST);
foo (2, VAR_LIST_PRESENT, DOUB, 3.0, PINT, &x, END_OF_LIST);
}