| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427 | /* Formatted output to strings, using POSIX/XSI format strings with positions.   Copyright (C) 2003, 2006-2007 Free Software Foundation, Inc.   Written by Bruno Haible <bruno@clisp.org>, 2003.   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   by the Free Software Foundation; either version 2, or (at your option)   any later version.   This program is distributed in the hope that it will be useful,   but WITHOUT ANY WARRANTY; without even the implied warranty of   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU   Library General Public License for more details.   You should have received a copy of the GNU Library General Public   License along with this program; if not, write to the Free Software   Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301,   USA.  */#ifdef HAVE_CONFIG_H# include <config.h>#endif#ifdef __GNUC__# define alloca __builtin_alloca# define HAVE_ALLOCA 1#else# ifdef _MSC_VER#  include <malloc.h>#  define alloca _alloca# else#  if defined HAVE_ALLOCA_H || defined _LIBC#   include <alloca.h>#  else#   ifdef _AIX #pragma alloca#   else#    ifndef allocachar *alloca ();#    endif#   endif#  endif# endif#endif#include <stdio.h>#if !HAVE_POSIX_PRINTF#include <errno.h>#include <limits.h>#include <stdlib.h>#include <string.h>/* Some systems, like OSF/1 4.0 and Woe32, don't have EOVERFLOW.  */#ifndef EOVERFLOW# define EOVERFLOW E2BIG#endif/* When building a DLL, we must export some functions.  Note that because   the functions are only defined for binary backward compatibility, we   don't need to use __declspec(dllimport) in any case.  */#if defined _MSC_VER && BUILDING_DLL# define DLL_EXPORTED __declspec(dllexport)#else# define DLL_EXPORTED#endif#define STATIC static/* This needs to be consistent with libgnuintl.h.in.  */#if defined __NetBSD__ || defined __BEOS__ || defined __CYGWIN__ || defined __MINGW32__/* Don't break __attribute__((format(printf,M,N))).   This redefinition is only possible because the libc in NetBSD, Cygwin,   mingw does not have a function __printf__.  */# define libintl_printf __printf__#endif/* Define auxiliary functions declared in "printf-args.h".  */#include "printf-args.c"/* Define auxiliary functions declared in "printf-parse.h".  */#include "printf-parse.c"/* Define functions declared in "vasnprintf.h".  */#define vasnprintf libintl_vasnprintf#include "vasnprintf.c"#if 0 /* not needed */#define asnprintf libintl_asnprintf#include "asnprintf.c"#endifDLL_EXPORTEDintlibintl_vfprintf (FILE *stream, const char *format, va_list args){  if (strchr (format, '$') == NULL)    return vfprintf (stream, format, args);  else    {      size_t length;      char *result = libintl_vasnprintf (NULL, &length, format, args);      int retval = -1;      if (result != NULL)	{	  size_t written = fwrite (result, 1, length, stream);	  free (result);	  if (written == length)	    {	      if (length > INT_MAX)		errno = EOVERFLOW;	      else		retval = length;	    }	}      return retval;    }}DLL_EXPORTEDintlibintl_fprintf (FILE *stream, const char *format, ...){  va_list args;  int retval;  va_start (args, format);  retval = libintl_vfprintf (stream, format, args);  va_end (args);  return retval;}DLL_EXPORTEDintlibintl_vprintf (const char *format, va_list args){  return libintl_vfprintf (stdout, format, args);}DLL_EXPORTEDintlibintl_printf (const char *format, ...){  va_list args;  int retval;  va_start (args, format);  retval = libintl_vprintf (format, args);  va_end (args);  return retval;}DLL_EXPORTEDintlibintl_vsprintf (char *resultbuf, const char *format, va_list args){  if (strchr (format, '$') == NULL)    return vsprintf (resultbuf, format, args);  else    {      size_t length = (size_t) ~0 / (4 * sizeof (char));      char *result = libintl_vasnprintf (resultbuf, &length, format, args);      if (result != resultbuf)	{	  free (result);	  return -1;	}      if (length > INT_MAX)	{	  errno = EOVERFLOW;	  return -1;	}      else	return length;    }}DLL_EXPORTEDintlibintl_sprintf (char *resultbuf, const char *format, ...){  va_list args;  int retval;  va_start (args, format);  retval = libintl_vsprintf (resultbuf, format, args);  va_end (args);  return retval;}#if HAVE_SNPRINTF# if HAVE_DECL__SNPRINTF   /* Windows.  */#  define system_vsnprintf _vsnprintf# else   /* Unix.  */#  define system_vsnprintf vsnprintf# endifDLL_EXPORTEDintlibintl_vsnprintf (char *resultbuf, size_t length, const char *format, va_list args){  if (strchr (format, '$') == NULL)    return system_vsnprintf (resultbuf, length, format, args);  else    {      size_t maxlength = length;      char *result = libintl_vasnprintf (resultbuf, &length, format, args);      if (result != resultbuf)	{	  if (maxlength > 0)	    {	      size_t pruned_length =		(length < maxlength ? length : maxlength - 1);	      memcpy (resultbuf, result, pruned_length);	      resultbuf[pruned_length] = '\0';	    }	  free (result);	}      if (length > INT_MAX)	{	  errno = EOVERFLOW;	  return -1;	}      else	return length;    }}DLL_EXPORTEDintlibintl_snprintf (char *resultbuf, size_t length, const char *format, ...){  va_list args;  int retval;  va_start (args, format);  retval = libintl_vsnprintf (resultbuf, length, format, args);  va_end (args);  return retval;}#endif#if HAVE_ASPRINTFDLL_EXPORTEDintlibintl_vasprintf (char **resultp, const char *format, va_list args){  size_t length;  char *result = libintl_vasnprintf (NULL, &length, format, args);  if (result == NULL)    return -1;  if (length > INT_MAX)    {      free (result);      errno = EOVERFLOW;      return -1;    }  *resultp = result;  return length;}DLL_EXPORTEDintlibintl_asprintf (char **resultp, const char *format, ...){  va_list args;  int retval;  va_start (args, format);  retval = libintl_vasprintf (resultp, format, args);  va_end (args);  return retval;}#endif#if HAVE_FWPRINTF#include <wchar.h>#define WIDE_CHAR_VERSION 1#include "wprintf-parse.h"/* Define auxiliary functions declared in "wprintf-parse.h".  */#define CHAR_T wchar_t#define DIRECTIVE wchar_t_directive#define DIRECTIVES wchar_t_directives#define PRINTF_PARSE wprintf_parse#include "printf-parse.c"/* Define functions declared in "vasnprintf.h".  */#define vasnwprintf libintl_vasnwprintf#include "vasnprintf.c"#if 0 /* not needed */#define asnwprintf libintl_asnwprintf#include "asnprintf.c"#endif# if HAVE_DECL__SNWPRINTF   /* Windows.  */#  define system_vswprintf _vsnwprintf# else   /* Unix.  */#  define system_vswprintf vswprintf# endifDLL_EXPORTEDintlibintl_vfwprintf (FILE *stream, const wchar_t *format, va_list args){  if (wcschr (format, '$') == NULL)    return vfwprintf (stream, format, args);  else    {      size_t length;      wchar_t *result = libintl_vasnwprintf (NULL, &length, format, args);      int retval = -1;      if (result != NULL)	{	  size_t i;	  for (i = 0; i < length; i++)	    if (fputwc (result[i], stream) == WEOF)	      break;	  free (result);	  if (i == length)	    {	      if (length > INT_MAX)		errno = EOVERFLOW;	      else		retval = length;	    }	}      return retval;    }}DLL_EXPORTEDintlibintl_fwprintf (FILE *stream, const wchar_t *format, ...){  va_list args;  int retval;  va_start (args, format);  retval = libintl_vfwprintf (stream, format, args);  va_end (args);  return retval;}DLL_EXPORTEDintlibintl_vwprintf (const wchar_t *format, va_list args){  return libintl_vfwprintf (stdout, format, args);}DLL_EXPORTEDintlibintl_wprintf (const wchar_t *format, ...){  va_list args;  int retval;  va_start (args, format);  retval = libintl_vwprintf (format, args);  va_end (args);  return retval;}DLL_EXPORTEDintlibintl_vswprintf (wchar_t *resultbuf, size_t length, const wchar_t *format, va_list args){  if (wcschr (format, '$') == NULL)    return system_vswprintf (resultbuf, length, format, args);  else    {      size_t maxlength = length;      wchar_t *result = libintl_vasnwprintf (resultbuf, &length, format, args);      if (result != resultbuf)	{	  if (maxlength > 0)	    {	      size_t pruned_length =		(length < maxlength ? length : maxlength - 1);	      memcpy (resultbuf, result, pruned_length * sizeof (wchar_t));	      resultbuf[pruned_length] = 0;	    }	  free (result);	  /* Unlike vsnprintf, which has to return the number of character that	     would have been produced if the resultbuf had been sufficiently	     large, the vswprintf function has to return a negative value if	     the resultbuf was not sufficiently large.  */	  if (length >= maxlength)	    return -1;	}      if (length > INT_MAX)	{	  errno = EOVERFLOW;	  return -1;	}      else	return length;    }}DLL_EXPORTEDintlibintl_swprintf (wchar_t *resultbuf, size_t length, const wchar_t *format, ...){  va_list args;  int retval;  va_start (args, format);  retval = libintl_vswprintf (resultbuf, length, format, args);  va_end (args);  return retval;}#endif#endif
 |