summaryrefslogtreecommitdiffstats
path: root/intl/vasnprintf.c
diff options
context:
space:
mode:
authorPedro J. Ruiz Lopez <holzplatten@es.gnu.org>2007-02-18 19:35:04 +0000
committerPedro J. Ruiz Lopez <holzplatten@es.gnu.org>2007-02-18 19:35:04 +0000
commitd49b34302a70ad948ce9cbf5778b1b39adb4286d (patch)
treed67ad1453f9380f549d880e5ffbc43df8ba63828 /intl/vasnprintf.c
parent80f3bd30c7521091c1dea118603b20a76c2a180c (diff)
downloadidutils-d49b34302a70ad948ce9cbf5778b1b39adb4286d.tar.gz
idutils-d49b34302a70ad948ce9cbf5778b1b39adb4286d.tar.bz2
idutils-d49b34302a70ad948ce9cbf5778b1b39adb4286d.zip
Upgrade to gettext 0.16.1
Diffstat (limited to 'intl/vasnprintf.c')
-rw-r--r--intl/vasnprintf.c84
1 files changed, 36 insertions, 48 deletions
diff --git a/intl/vasnprintf.c b/intl/vasnprintf.c
index f59968f..8b07310 100644
--- a/intl/vasnprintf.c
+++ b/intl/vasnprintf.c
@@ -1,5 +1,5 @@
/* vsprintf with automatic memory allocation.
- Copyright (C) 1999, 2002-2005 Free Software Foundation, Inc.
+ Copyright (C) 1999, 2002-2006 Free Software Foundation, Inc.
This program is free software; you can redistribute it and/or modify it
under the terms of the GNU Library General Public License as published
@@ -23,9 +23,7 @@
# define _GNU_SOURCE 1
#endif
-#ifdef HAVE_CONFIG_H
-# include <config.h>
-#endif
+#include <config.h>
#ifndef IN_LIBINTL
# include <alloca.h>
#endif
@@ -41,7 +39,7 @@
#include <stdlib.h> /* abort(), malloc(), realloc(), free() */
#include <string.h> /* memcpy(), strlen() */
#include <errno.h> /* errno */
-#include <limits.h> /* CHAR_BIT, INT_MAX */
+#include <limits.h> /* CHAR_BIT */
#include <float.h> /* DBL_MAX_EXP, LDBL_MAX_EXP */
#if WIDE_CHAR_VERSION
# include "wprintf-parse.h"
@@ -52,11 +50,6 @@
/* Checked size_t computations. */
#include "xsize.h"
-/* Some systems, like OSF/1 4.0 and Woe32, don't have EOVERFLOW. */
-#ifndef EOVERFLOW
-# define EOVERFLOW E2BIG
-#endif
-
#ifdef HAVE_WCHAR_T
# ifdef HAVE_WCSLEN
# define local_wcslen wcslen
@@ -256,7 +249,7 @@ VASNPRINTF (CHAR_T *resultbuf, size_t *lengthp, const CHAR_T *format, va_list ar
case TYPE_COUNT_LONGINT_POINTER:
*a.arg[dp->arg_index].a.a_count_longint_pointer = length;
break;
-#ifdef HAVE_LONG_LONG
+#ifdef HAVE_LONG_LONG_INT
case TYPE_COUNT_LONGLONGINT_POINTER:
*a.arg[dp->arg_index].a.a_count_longlongint_pointer = length;
break;
@@ -330,44 +323,43 @@ VASNPRINTF (CHAR_T *resultbuf, size_t *lengthp, const CHAR_T *format, va_list ar
{
case 'd': case 'i': case 'u':
-# ifdef HAVE_LONG_LONG
+# ifdef HAVE_LONG_LONG_INT
if (type == TYPE_LONGLONGINT || type == TYPE_ULONGLONGINT)
tmp_length =
(unsigned int) (sizeof (unsigned long long) * CHAR_BIT
* 0.30103 /* binary -> decimal */
- * 2 /* estimate for FLAG_GROUP */
)
- + 1 /* turn floor into ceil */
- + 1; /* account for leading sign */
+ + 1; /* turn floor into ceil */
else
# endif
if (type == TYPE_LONGINT || type == TYPE_ULONGINT)
tmp_length =
(unsigned int) (sizeof (unsigned long) * CHAR_BIT
* 0.30103 /* binary -> decimal */
- * 2 /* estimate for FLAG_GROUP */
)
- + 1 /* turn floor into ceil */
- + 1; /* account for leading sign */
+ + 1; /* turn floor into ceil */
else
tmp_length =
(unsigned int) (sizeof (unsigned int) * CHAR_BIT
* 0.30103 /* binary -> decimal */
- * 2 /* estimate for FLAG_GROUP */
)
- + 1 /* turn floor into ceil */
- + 1; /* account for leading sign */
+ + 1; /* turn floor into ceil */
+ if (tmp_length < precision)
+ tmp_length = precision;
+ /* Multiply by 2, as an estimate for FLAG_GROUP. */
+ tmp_length = xsum (tmp_length, tmp_length);
+ /* Add 1, to account for a leading sign. */
+ tmp_length = xsum (tmp_length, 1);
break;
case 'o':
-# ifdef HAVE_LONG_LONG
+# ifdef HAVE_LONG_LONG_INT
if (type == TYPE_LONGLONGINT || type == TYPE_ULONGLONGINT)
tmp_length =
(unsigned int) (sizeof (unsigned long long) * CHAR_BIT
* 0.333334 /* binary -> octal */
)
- + 1 /* turn floor into ceil */
- + 1; /* account for leading sign */
+ + 1; /* turn floor into ceil */
else
# endif
if (type == TYPE_LONGINT || type == TYPE_ULONGINT)
@@ -375,26 +367,27 @@ VASNPRINTF (CHAR_T *resultbuf, size_t *lengthp, const CHAR_T *format, va_list ar
(unsigned int) (sizeof (unsigned long) * CHAR_BIT
* 0.333334 /* binary -> octal */
)
- + 1 /* turn floor into ceil */
- + 1; /* account for leading sign */
+ + 1; /* turn floor into ceil */
else
tmp_length =
(unsigned int) (sizeof (unsigned int) * CHAR_BIT
* 0.333334 /* binary -> octal */
)
- + 1 /* turn floor into ceil */
- + 1; /* account for leading sign */
+ + 1; /* turn floor into ceil */
+ if (tmp_length < precision)
+ tmp_length = precision;
+ /* Add 1, to account for a leading sign. */
+ tmp_length = xsum (tmp_length, 1);
break;
case 'x': case 'X':
-# ifdef HAVE_LONG_LONG
+# ifdef HAVE_LONG_LONG_INT
if (type == TYPE_LONGLONGINT || type == TYPE_ULONGLONGINT)
tmp_length =
(unsigned int) (sizeof (unsigned long long) * CHAR_BIT
* 0.25 /* binary -> hexadecimal */
)
- + 1 /* turn floor into ceil */
- + 2; /* account for leading sign or alternate form */
+ + 1; /* turn floor into ceil */
else
# endif
if (type == TYPE_LONGINT || type == TYPE_ULONGINT)
@@ -402,15 +395,17 @@ VASNPRINTF (CHAR_T *resultbuf, size_t *lengthp, const CHAR_T *format, va_list ar
(unsigned int) (sizeof (unsigned long) * CHAR_BIT
* 0.25 /* binary -> hexadecimal */
)
- + 1 /* turn floor into ceil */
- + 2; /* account for leading sign or alternate form */
+ + 1; /* turn floor into ceil */
else
tmp_length =
(unsigned int) (sizeof (unsigned int) * CHAR_BIT
* 0.25 /* binary -> hexadecimal */
)
- + 1 /* turn floor into ceil */
- + 2; /* account for leading sign or alternate form */
+ + 1; /* turn floor into ceil */
+ if (tmp_length < precision)
+ tmp_length = precision;
+ /* Add 2, to account for a leading sign or alternate form. */
+ tmp_length = xsum (tmp_length, 2);
break;
case 'f': case 'F':
@@ -533,7 +528,7 @@ VASNPRINTF (CHAR_T *resultbuf, size_t *lengthp, const CHAR_T *format, va_list ar
switch (type)
{
-#ifdef HAVE_LONG_LONG
+#ifdef HAVE_LONG_LONG_INT
case TYPE_LONGLONGINT:
case TYPE_ULONGLONGINT:
*p++ = 'l';
@@ -687,7 +682,7 @@ VASNPRINTF (CHAR_T *resultbuf, size_t *lengthp, const CHAR_T *format, va_list ar
SNPRINTF_BUF (arg);
}
break;
-#ifdef HAVE_LONG_LONG
+#ifdef HAVE_LONG_LONG_INT
case TYPE_LONGLONGINT:
{
long long int arg = a.arg[dp->arg_index].a.a_longlongint;
@@ -868,19 +863,12 @@ VASNPRINTF (CHAR_T *resultbuf, size_t *lengthp, const CHAR_T *format, va_list ar
free (buf_malloced);
CLEANUP ();
*lengthp = length;
- if (length > INT_MAX)
- goto length_overflow;
+ /* Note that we can produce a big string of a length > INT_MAX. POSIX
+ says that snprintf() fails with errno = EOVERFLOW in this case, but
+ that's only because snprintf() returns an 'int'. This function does
+ not have this limitation. */
return result;
- length_overflow:
- /* We could produce such a big string, but its length doesn't fit into
- an 'int'. POSIX says that snprintf() fails with errno = EOVERFLOW in
- this case. */
- if (result != resultbuf)
- free (result);
- errno = EOVERFLOW;
- return NULL;
-
out_of_memory:
if (!(result == resultbuf || result == NULL))
free (result);