Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Using asprintf() on windows

I have written a C program which works perfectly on linux, but when I compile it on windows, it gives me an error saying that asprintf() is undefined. It should be a part of the stdio library but it seems that many compilers do not include it. Which compiler can I use for windows which will allow me to use the asprintf() function? I have tried multiple compilers and none seem to define it so far.

like image 765
Vasundhara Mehta Avatar asked Oct 20 '16 16:10

Vasundhara Mehta


1 Answers

The asprintf() function is not part of the C language and it is not available on all platforms. The fact that Linux has it is unusual.

You can write your own using _vscprintf and _vsprintf_s.

int vasprintf(char **strp, const char *fmt, va_list ap) {
    // _vscprintf tells you how big the buffer needs to be
    int len = _vscprintf(fmt, ap);
    if (len == -1) {
        return -1;
    }
    size_t size = (size_t)len + 1;
    char *str = malloc(size);
    if (!str) {
        return -1;
    }
    // _vsprintf_s is the "secure" version of vsprintf
    int r = _vsprintf_s(str, len + 1, fmt, ap);
    if (r == -1) {
        free(str);
        return -1;
    }
    *strp = str;
    return r;
}

This is from memory but it should be very close to how you would write vasprintf for the Visual Studio runtime.

The use of _vscprintf and _vsprintf_s are oddities unique to the Microsoft C runtime, you wouldn't write the code this way on Linux or OS X. The _s versions in particular, while standardized, in practice are not often encountered outside the Microsoft ecosystem, and _vscprintf doesn't even exist elsewhere.

Of course, asprintf is just a wrapper around vasprintf:

int asprintf(char **strp, const char *fmt, ...) {
    va_list ap;
    va_start(ap, fmt);
    int r = vasprintf(strp, fmt, ap);
    va_end(ap);
    return r;
}

This is not a "portable" way to write asprintf, but if your only goal is to support Linux + Darwin + Windows, then this is the best way to do that.

like image 55
Dietrich Epp Avatar answered Sep 18 '22 01:09

Dietrich Epp