Forward an invocation of a variadic function in C

If you don't have a function analogous to vfprintf that takes a va_list instead of a variable number of arguments, you can't do it. See http://c-faq.com/varargs/handoff.html.

Example:

void myfun(const char *fmt, va_list argp) {
    vfprintf(stderr, fmt, argp);
}

C99 supports macros with variadic arguments; depending on your compiler, you might be able to declare a macro that does what you want:

#define my_printf(format, ...) \
    do { \
        fprintf(stderr, "Calling printf with fmt %s\n", format); \
        some_other_variadac_function(format, ##__VA_ARGS__); \
    } while(0)

In general, though, the best solution is to use the va_list form of the function you're trying to wrap, should one exist.


Not directly, however it is common (and you will find almost universally the case in the standard library) for variadic functions to come in pairs with a varargs style alternative function. e.g. printf/vprintf

The v... functions take a va_list parameter, the implementation of which is often done with compiler specific 'macro magic', but you are guaranteed that calling the v... style function from a variadic function like this will work:

#include <stdarg.h>

int m_printf(char *fmt, ...)
{
    int ret;

    /* Declare a va_list type variable */
    va_list myargs;

    /* Initialise the va_list variable with the ... after fmt */

    va_start(myargs, fmt);

    /* Forward the '...' to vprintf */
    ret = vprintf(fmt, myargs);

    /* Clean up the va_list */
    va_end(myargs);

    return ret;
}

This should give you the effect that you are looking for.

If you are considering writing a variadic library function you should also consider making a va_list style companion available as part of the library. As you can see from your question, it can be prove useful for your users.

Tags:

C

Variadic