[GRASS5] snprintf and other compile errors on IRIX

Carl Worth cworth at east.isi.edu
Wed Apr 24 09:37:07 EDT 2002


On Apr 23, Eric G. Miller wrote:
 > It'd be nice to have a function that was a combination of sprintf and
 > strdup:  char * G_strdupf(const char *fmt, ...); ??

Absolutely.

Some systems have an asprintf which is printf with allocation. It's
even harder to find than snprintf though. :(

Instead, if you do have snprintf, (one that is capable of returning
indication of whether N was large enough)., then it's pretty easy to
make a function just like what you want. In other projects, I've been
happily using such a function that I snitched from the printf(3) page
on a Linux system. I rarely think about string lengths anymore.

I'll include the function I'm using for reference, (but it doesn't
seem like GRASS could use anything like this yet).

 > String handling in C is such a PITA...

Tell me about it.

-Carl

PS. Here's the code I use regularly, (I actually pass in the address
of the char * of interest rather than returning it as you propose).

#include <stdio.h>
#include <stdlib.h>
#include <stdarg.h>
#include <string.h>

int sprintf_alloc(char **str, const char *fmt, ...)
{
    int ret;
    va_list ap;

    va_start(ap, fmt);
    ret = va_sprintf_alloc(str, fmt, ap);
    va_end(ap);

    return ret;
}

/* ripped more or less straight out of PRINTF(3) */
int va_sprintf_alloc(char **str, const char *fmt, va_list ap)
{
    char *new_str;
    /* Guess we need no more than 100 bytes. */
    int n, size = 100;

    if ((*str = malloc (size)) == NULL)
        return -1;
    while (1) {
        /* Try to print in the allocated space. */
        n = vsnprintf (*str, size, fmt, ap);
        /* If that worked, return the size. */
        if (n > -1 && n < size)
            return n;
        /* Else try again with more space. */
        if (n > -1)    /* glibc 2.1 */
            size = n+1; /* precisely what is needed */
        else           /* glibc 2.0 */
            size *= 2;  /* twice the old size */
        new_str = realloc(*str, size);
        if (new_str == NULL) {
            free(*str);
            *str = NULL;
            return -1;
        }
        *str = new_str;
    }
}

-- 
Carl Worth                                        
USC Information Sciences Institute                 cworth at east.isi.edu
3811 N. Fairfax Dr. #200, Arlington VA 22203		  703-812-3725



More information about the grass-dev mailing list