~ubuntu-branches/ubuntu/precise/wget/precise-proposed

« back to all changes in this revision

Viewing changes to lib/vasnprintf.c

  • Committer: Bazaar Package Importer
  • Author(s): Steve Langasek
  • Date: 2011-10-19 00:00:09 UTC
  • mfrom: (2.1.13 sid)
  • Revision ID: james.westby@ubuntu.com-20111019000009-8p33w3wz4b1rdri0
Tags: 1.13-1ubuntu1
* Merge from Debian unstable, remaining changes:
  - Add wget-udeb to ship wget.gnu as alternative to busybox wget
    implementation.
  - Depend on libssl-dev 0.9.8k-7ubuntu4 (LP: #503339)
* Dropped changes, superseded in Debian:
  - Keep build dependencies in main:
    + debian/control: remove info2man build-dep
    + debian/patches/series: disable wget-infopod_generated_manpage
  - Mark wget Multi-Arch: foreign, so packages that aren't of the same arch
    can depend on it.
* Pass --with-ssl=openssl; we don't want to use gnutls, there's no udeb for
  it.
* Add a second build pass for the udeb, so we can build without libidn.

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/* -*- buffer-read-only: t -*- vi: set ro: */
 
2
/* DO NOT EDIT! GENERATED AUTOMATICALLY! */
 
3
/* vsprintf with automatic memory allocation.
 
4
   Copyright (C) 1999, 2002-2011 Free Software Foundation, Inc.
 
5
 
 
6
   This program is free software; you can redistribute it and/or modify
 
7
   it under the terms of the GNU General Public License as published by
 
8
   the Free Software Foundation; either version 3, or (at your option)
 
9
   any later version.
 
10
 
 
11
   This program is distributed in the hope that it will be useful,
 
12
   but WITHOUT ANY WARRANTY; without even the implied warranty of
 
13
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 
14
   GNU General Public License for more details.
 
15
 
 
16
   You should have received a copy of the GNU General Public License along
 
17
   with this program; if not, write to the Free Software Foundation,
 
18
   Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.  */
 
19
 
 
20
/* This file can be parametrized with the following macros:
 
21
     VASNPRINTF         The name of the function being defined.
 
22
     FCHAR_T            The element type of the format string.
 
23
     DCHAR_T            The element type of the destination (result) string.
 
24
     FCHAR_T_ONLY_ASCII Set to 1 to enable verification that all characters
 
25
                        in the format string are ASCII. MUST be set if
 
26
                        FCHAR_T and DCHAR_T are not the same type.
 
27
     DIRECTIVE          Structure denoting a format directive.
 
28
                        Depends on FCHAR_T.
 
29
     DIRECTIVES         Structure denoting the set of format directives of a
 
30
                        format string.  Depends on FCHAR_T.
 
31
     PRINTF_PARSE       Function that parses a format string.
 
32
                        Depends on FCHAR_T.
 
33
     DCHAR_CPY          memcpy like function for DCHAR_T[] arrays.
 
34
     DCHAR_SET          memset like function for DCHAR_T[] arrays.
 
35
     DCHAR_MBSNLEN      mbsnlen like function for DCHAR_T[] arrays.
 
36
     SNPRINTF           The system's snprintf (or similar) function.
 
37
                        This may be either snprintf or swprintf.
 
38
     TCHAR_T            The element type of the argument and result string
 
39
                        of the said SNPRINTF function.  This may be either
 
40
                        char or wchar_t.  The code exploits that
 
41
                        sizeof (TCHAR_T) | sizeof (DCHAR_T) and
 
42
                        alignof (TCHAR_T) <= alignof (DCHAR_T).
 
43
     DCHAR_IS_TCHAR     Set to 1 if DCHAR_T and TCHAR_T are the same type.
 
44
     DCHAR_CONV_FROM_ENCODING A function to convert from char[] to DCHAR[].
 
45
     DCHAR_IS_UINT8_T   Set to 1 if DCHAR_T is uint8_t.
 
46
     DCHAR_IS_UINT16_T  Set to 1 if DCHAR_T is uint16_t.
 
47
     DCHAR_IS_UINT32_T  Set to 1 if DCHAR_T is uint32_t.  */
 
48
 
 
49
/* Tell glibc's <stdio.h> to provide a prototype for snprintf().
 
50
   This must come before <config.h> because <config.h> may include
 
51
   <features.h>, and once <features.h> has been included, it's too late.  */
 
52
#ifndef _GNU_SOURCE
 
53
# define _GNU_SOURCE    1
 
54
#endif
 
55
 
 
56
#ifndef VASNPRINTF
 
57
# include <config.h>
 
58
#endif
 
59
#ifndef IN_LIBINTL
 
60
# include <alloca.h>
 
61
#endif
 
62
 
 
63
/* Specification.  */
 
64
#ifndef VASNPRINTF
 
65
# if WIDE_CHAR_VERSION
 
66
#  include "vasnwprintf.h"
 
67
# else
 
68
#  include "vasnprintf.h"
 
69
# endif
 
70
#endif
 
71
 
 
72
#include <locale.h>     /* localeconv() */
 
73
#include <stdio.h>      /* snprintf(), sprintf() */
 
74
#include <stdlib.h>     /* abort(), malloc(), realloc(), free() */
 
75
#include <string.h>     /* memcpy(), strlen() */
 
76
#include <errno.h>      /* errno */
 
77
#include <limits.h>     /* CHAR_BIT */
 
78
#include <float.h>      /* DBL_MAX_EXP, LDBL_MAX_EXP */
 
79
#if HAVE_NL_LANGINFO
 
80
# include <langinfo.h>
 
81
#endif
 
82
#ifndef VASNPRINTF
 
83
# if WIDE_CHAR_VERSION
 
84
#  include "wprintf-parse.h"
 
85
# else
 
86
#  include "printf-parse.h"
 
87
# endif
 
88
#endif
 
89
 
 
90
/* Checked size_t computations.  */
 
91
#include "xsize.h"
 
92
 
 
93
#include "verify.h"
 
94
 
 
95
#if (NEED_PRINTF_DOUBLE || NEED_PRINTF_LONG_DOUBLE) && !defined IN_LIBINTL
 
96
# include <math.h>
 
97
# include "float+.h"
 
98
#endif
 
99
 
 
100
#if (NEED_PRINTF_DOUBLE || NEED_PRINTF_INFINITE_DOUBLE) && !defined IN_LIBINTL
 
101
# include <math.h>
 
102
# include "isnand-nolibm.h"
 
103
#endif
 
104
 
 
105
#if (NEED_PRINTF_LONG_DOUBLE || NEED_PRINTF_INFINITE_LONG_DOUBLE) && !defined IN_LIBINTL
 
106
# include <math.h>
 
107
# include "isnanl-nolibm.h"
 
108
# include "fpucw.h"
 
109
#endif
 
110
 
 
111
#if (NEED_PRINTF_DIRECTIVE_A || NEED_PRINTF_DOUBLE) && !defined IN_LIBINTL
 
112
# include <math.h>
 
113
# include "isnand-nolibm.h"
 
114
# include "printf-frexp.h"
 
115
#endif
 
116
 
 
117
#if (NEED_PRINTF_DIRECTIVE_A || NEED_PRINTF_LONG_DOUBLE) && !defined IN_LIBINTL
 
118
# include <math.h>
 
119
# include "isnanl-nolibm.h"
 
120
# include "printf-frexpl.h"
 
121
# include "fpucw.h"
 
122
#endif
 
123
 
 
124
/* Default parameters.  */
 
125
#ifndef VASNPRINTF
 
126
# if WIDE_CHAR_VERSION
 
127
#  define VASNPRINTF vasnwprintf
 
128
#  define FCHAR_T wchar_t
 
129
#  define DCHAR_T wchar_t
 
130
#  define TCHAR_T wchar_t
 
131
#  define DCHAR_IS_TCHAR 1
 
132
#  define DIRECTIVE wchar_t_directive
 
133
#  define DIRECTIVES wchar_t_directives
 
134
#  define PRINTF_PARSE wprintf_parse
 
135
#  define DCHAR_CPY wmemcpy
 
136
#  define DCHAR_SET wmemset
 
137
# else
 
138
#  define VASNPRINTF vasnprintf
 
139
#  define FCHAR_T char
 
140
#  define DCHAR_T char
 
141
#  define TCHAR_T char
 
142
#  define DCHAR_IS_TCHAR 1
 
143
#  define DIRECTIVE char_directive
 
144
#  define DIRECTIVES char_directives
 
145
#  define PRINTF_PARSE printf_parse
 
146
#  define DCHAR_CPY memcpy
 
147
#  define DCHAR_SET memset
 
148
# endif
 
149
#endif
 
150
#if WIDE_CHAR_VERSION
 
151
  /* TCHAR_T is wchar_t.  */
 
152
# define USE_SNPRINTF 1
 
153
# if HAVE_DECL__SNWPRINTF
 
154
   /* On Windows, the function swprintf() has a different signature than
 
155
      on Unix; we use the function _snwprintf() or - on mingw - snwprintf()
 
156
      instead.  The mingw function snwprintf() has fewer bugs than the
 
157
      MSVCRT function _snwprintf(), so prefer that.  */
 
158
#  if defined __MINGW32__
 
159
#   define SNPRINTF snwprintf
 
160
#  else
 
161
#   define SNPRINTF _snwprintf
 
162
#  endif
 
163
# else
 
164
   /* Unix.  */
 
165
#  define SNPRINTF swprintf
 
166
# endif
 
167
#else
 
168
  /* TCHAR_T is char.  */
 
169
  /* Use snprintf if it exists under the name 'snprintf' or '_snprintf'.
 
170
     But don't use it on BeOS, since BeOS snprintf produces no output if the
 
171
     size argument is >= 0x3000000.
 
172
     Also don't use it on Linux libc5, since there snprintf with size = 1
 
173
     writes any output without bounds, like sprintf.  */
 
174
# if (HAVE_DECL__SNPRINTF || HAVE_SNPRINTF) && !defined __BEOS__ && !(__GNU_LIBRARY__ == 1)
 
175
#  define USE_SNPRINTF 1
 
176
# else
 
177
#  define USE_SNPRINTF 0
 
178
# endif
 
179
# if HAVE_DECL__SNPRINTF
 
180
   /* Windows.  The mingw function snprintf() has fewer bugs than the MSVCRT
 
181
      function _snprintf(), so prefer that.  */
 
182
#  if defined __MINGW32__
 
183
#   define SNPRINTF snprintf
 
184
    /* Here we need to call the native snprintf, not rpl_snprintf.  */
 
185
#   undef snprintf
 
186
#  else
 
187
#   define SNPRINTF _snprintf
 
188
#  endif
 
189
# else
 
190
   /* Unix.  */
 
191
#  define SNPRINTF snprintf
 
192
   /* Here we need to call the native snprintf, not rpl_snprintf.  */
 
193
#  undef snprintf
 
194
# endif
 
195
#endif
 
196
/* Here we need to call the native sprintf, not rpl_sprintf.  */
 
197
#undef sprintf
 
198
 
 
199
/* GCC >= 4.0 with -Wall emits unjustified "... may be used uninitialized"
 
200
   warnings in this file.  Use -Dlint to suppress them.  */
 
201
#ifdef lint
 
202
# define IF_LINT(Code) Code
 
203
#else
 
204
# define IF_LINT(Code) /* empty */
 
205
#endif
 
206
 
 
207
/* Avoid some warnings from "gcc -Wshadow".
 
208
   This file doesn't use the exp() and remainder() functions.  */
 
209
#undef exp
 
210
#define exp expo
 
211
#undef remainder
 
212
#define remainder rem
 
213
 
 
214
#if (!USE_SNPRINTF || !HAVE_SNPRINTF_RETVAL_C99) && !WIDE_CHAR_VERSION
 
215
# if (HAVE_STRNLEN && !defined _AIX)
 
216
#  define local_strnlen strnlen
 
217
# else
 
218
#  ifndef local_strnlen_defined
 
219
#   define local_strnlen_defined 1
 
220
static size_t
 
221
local_strnlen (const char *string, size_t maxlen)
 
222
{
 
223
  const char *end = memchr (string, '\0', maxlen);
 
224
  return end ? (size_t) (end - string) : maxlen;
 
225
}
 
226
#  endif
 
227
# endif
 
228
#endif
 
229
 
 
230
#if (((!USE_SNPRINTF || !HAVE_SNPRINTF_RETVAL_C99) && WIDE_CHAR_VERSION) || ((!USE_SNPRINTF || !HAVE_SNPRINTF_RETVAL_C99 || (NEED_PRINTF_DIRECTIVE_LS && !defined IN_LIBINTL)) && !WIDE_CHAR_VERSION && DCHAR_IS_TCHAR)) && HAVE_WCHAR_T
 
231
# if HAVE_WCSLEN
 
232
#  define local_wcslen wcslen
 
233
# else
 
234
   /* Solaris 2.5.1 has wcslen() in a separate library libw.so. To avoid
 
235
      a dependency towards this library, here is a local substitute.
 
236
      Define this substitute only once, even if this file is included
 
237
      twice in the same compilation unit.  */
 
238
#  ifndef local_wcslen_defined
 
239
#   define local_wcslen_defined 1
 
240
static size_t
 
241
local_wcslen (const wchar_t *s)
 
242
{
 
243
  const wchar_t *ptr;
 
244
 
 
245
  for (ptr = s; *ptr != (wchar_t) 0; ptr++)
 
246
    ;
 
247
  return ptr - s;
 
248
}
 
249
#  endif
 
250
# endif
 
251
#endif
 
252
 
 
253
#if (!USE_SNPRINTF || !HAVE_SNPRINTF_RETVAL_C99) && HAVE_WCHAR_T && WIDE_CHAR_VERSION
 
254
# if HAVE_WCSNLEN
 
255
#  define local_wcsnlen wcsnlen
 
256
# else
 
257
#  ifndef local_wcsnlen_defined
 
258
#   define local_wcsnlen_defined 1
 
259
static size_t
 
260
local_wcsnlen (const wchar_t *s, size_t maxlen)
 
261
{
 
262
  const wchar_t *ptr;
 
263
 
 
264
  for (ptr = s; maxlen > 0 && *ptr != (wchar_t) 0; ptr++, maxlen--)
 
265
    ;
 
266
  return ptr - s;
 
267
}
 
268
#  endif
 
269
# endif
 
270
#endif
 
271
 
 
272
#if (NEED_PRINTF_DIRECTIVE_A || NEED_PRINTF_LONG_DOUBLE || NEED_PRINTF_INFINITE_LONG_DOUBLE || NEED_PRINTF_DOUBLE || NEED_PRINTF_INFINITE_DOUBLE) && !defined IN_LIBINTL
 
273
/* Determine the decimal-point character according to the current locale.  */
 
274
# ifndef decimal_point_char_defined
 
275
#  define decimal_point_char_defined 1
 
276
static char
 
277
decimal_point_char (void)
 
278
{
 
279
  const char *point;
 
280
  /* Determine it in a multithread-safe way.  We know nl_langinfo is
 
281
     multithread-safe on glibc systems and MacOS X systems, but is not required
 
282
     to be multithread-safe by POSIX.  sprintf(), however, is multithread-safe.
 
283
     localeconv() is rarely multithread-safe.  */
 
284
#  if HAVE_NL_LANGINFO && (__GLIBC__ || defined __UCLIBC__ || (defined __APPLE__ && defined __MACH__))
 
285
  point = nl_langinfo (RADIXCHAR);
 
286
#  elif 1
 
287
  char pointbuf[5];
 
288
  sprintf (pointbuf, "%#.0f", 1.0);
 
289
  point = &pointbuf[1];
 
290
#  else
 
291
  point = localeconv () -> decimal_point;
 
292
#  endif
 
293
  /* The decimal point is always a single byte: either '.' or ','.  */
 
294
  return (point[0] != '\0' ? point[0] : '.');
 
295
}
 
296
# endif
 
297
#endif
 
298
 
 
299
#if NEED_PRINTF_INFINITE_DOUBLE && !NEED_PRINTF_DOUBLE && !defined IN_LIBINTL
 
300
 
 
301
/* Equivalent to !isfinite(x) || x == 0, but does not require libm.  */
 
302
static int
 
303
is_infinite_or_zero (double x)
 
304
{
 
305
  return isnand (x) || x + x == x;
 
306
}
 
307
 
 
308
#endif
 
309
 
 
310
#if NEED_PRINTF_INFINITE_LONG_DOUBLE && !NEED_PRINTF_LONG_DOUBLE && !defined IN_LIBINTL
 
311
 
 
312
/* Equivalent to !isfinite(x) || x == 0, but does not require libm.  */
 
313
static int
 
314
is_infinite_or_zerol (long double x)
 
315
{
 
316
  return isnanl (x) || x + x == x;
 
317
}
 
318
 
 
319
#endif
 
320
 
 
321
#if (NEED_PRINTF_LONG_DOUBLE || NEED_PRINTF_DOUBLE) && !defined IN_LIBINTL
 
322
 
 
323
/* Converting 'long double' to decimal without rare rounding bugs requires
 
324
   real bignums.  We use the naming conventions of GNU gmp, but vastly simpler
 
325
   (and slower) algorithms.  */
 
326
 
 
327
typedef unsigned int mp_limb_t;
 
328
# define GMP_LIMB_BITS 32
 
329
verify (sizeof (mp_limb_t) * CHAR_BIT == GMP_LIMB_BITS);
 
330
 
 
331
typedef unsigned long long mp_twolimb_t;
 
332
# define GMP_TWOLIMB_BITS 64
 
333
verify (sizeof (mp_twolimb_t) * CHAR_BIT == GMP_TWOLIMB_BITS);
 
334
 
 
335
/* Representation of a bignum >= 0.  */
 
336
typedef struct
 
337
{
 
338
  size_t nlimbs;
 
339
  mp_limb_t *limbs; /* Bits in little-endian order, allocated with malloc().  */
 
340
} mpn_t;
 
341
 
 
342
/* Compute the product of two bignums >= 0.
 
343
   Return the allocated memory in case of success, NULL in case of memory
 
344
   allocation failure.  */
 
345
static void *
 
346
multiply (mpn_t src1, mpn_t src2, mpn_t *dest)
 
347
{
 
348
  const mp_limb_t *p1;
 
349
  const mp_limb_t *p2;
 
350
  size_t len1;
 
351
  size_t len2;
 
352
 
 
353
  if (src1.nlimbs <= src2.nlimbs)
 
354
    {
 
355
      len1 = src1.nlimbs;
 
356
      p1 = src1.limbs;
 
357
      len2 = src2.nlimbs;
 
358
      p2 = src2.limbs;
 
359
    }
 
360
  else
 
361
    {
 
362
      len1 = src2.nlimbs;
 
363
      p1 = src2.limbs;
 
364
      len2 = src1.nlimbs;
 
365
      p2 = src1.limbs;
 
366
    }
 
367
  /* Now 0 <= len1 <= len2.  */
 
368
  if (len1 == 0)
 
369
    {
 
370
      /* src1 or src2 is zero.  */
 
371
      dest->nlimbs = 0;
 
372
      dest->limbs = (mp_limb_t *) malloc (1);
 
373
    }
 
374
  else
 
375
    {
 
376
      /* Here 1 <= len1 <= len2.  */
 
377
      size_t dlen;
 
378
      mp_limb_t *dp;
 
379
      size_t k, i, j;
 
380
 
 
381
      dlen = len1 + len2;
 
382
      dp = (mp_limb_t *) malloc (dlen * sizeof (mp_limb_t));
 
383
      if (dp == NULL)
 
384
        return NULL;
 
385
      for (k = len2; k > 0; )
 
386
        dp[--k] = 0;
 
387
      for (i = 0; i < len1; i++)
 
388
        {
 
389
          mp_limb_t digit1 = p1[i];
 
390
          mp_twolimb_t carry = 0;
 
391
          for (j = 0; j < len2; j++)
 
392
            {
 
393
              mp_limb_t digit2 = p2[j];
 
394
              carry += (mp_twolimb_t) digit1 * (mp_twolimb_t) digit2;
 
395
              carry += dp[i + j];
 
396
              dp[i + j] = (mp_limb_t) carry;
 
397
              carry = carry >> GMP_LIMB_BITS;
 
398
            }
 
399
          dp[i + len2] = (mp_limb_t) carry;
 
400
        }
 
401
      /* Normalise.  */
 
402
      while (dlen > 0 && dp[dlen - 1] == 0)
 
403
        dlen--;
 
404
      dest->nlimbs = dlen;
 
405
      dest->limbs = dp;
 
406
    }
 
407
  return dest->limbs;
 
408
}
 
409
 
 
410
/* Compute the quotient of a bignum a >= 0 and a bignum b > 0.
 
411
   a is written as  a = q * b + r  with 0 <= r < b.  q is the quotient, r
 
412
   the remainder.
 
413
   Finally, round-to-even is performed: If r > b/2 or if r = b/2 and q is odd,
 
414
   q is incremented.
 
415
   Return the allocated memory in case of success, NULL in case of memory
 
416
   allocation failure.  */
 
417
static void *
 
418
divide (mpn_t a, mpn_t b, mpn_t *q)
 
419
{
 
420
  /* Algorithm:
 
421
     First normalise a and b: a=[a[m-1],...,a[0]], b=[b[n-1],...,b[0]]
 
422
     with m>=0 and n>0 (in base beta = 2^GMP_LIMB_BITS).
 
423
     If m<n, then q:=0 and r:=a.
 
424
     If m>=n=1, perform a single-precision division:
 
425
       r:=0, j:=m,
 
426
       while j>0 do
 
427
         {Here (q[m-1]*beta^(m-1)+...+q[j]*beta^j) * b[0] + r*beta^j =
 
428
               = a[m-1]*beta^(m-1)+...+a[j]*beta^j und 0<=r<b[0]<beta}
 
429
         j:=j-1, r:=r*beta+a[j], q[j]:=floor(r/b[0]), r:=r-b[0]*q[j].
 
430
       Normalise [q[m-1],...,q[0]], yields q.
 
431
     If m>=n>1, perform a multiple-precision division:
 
432
       We have a/b < beta^(m-n+1).
 
433
       s:=intDsize-1-(highest bit in b[n-1]), 0<=s<intDsize.
 
434
       Shift a and b left by s bits, copying them. r:=a.
 
435
       r=[r[m],...,r[0]], b=[b[n-1],...,b[0]] with b[n-1]>=beta/2.
 
436
       For j=m-n,...,0: {Here 0 <= r < b*beta^(j+1).}
 
437
         Compute q* :
 
438
           q* := floor((r[j+n]*beta+r[j+n-1])/b[n-1]).
 
439
           In case of overflow (q* >= beta) set q* := beta-1.
 
440
           Compute c2 := ((r[j+n]*beta+r[j+n-1]) - q* * b[n-1])*beta + r[j+n-2]
 
441
           and c3 := b[n-2] * q*.
 
442
           {We have 0 <= c2 < 2*beta^2, even 0 <= c2 < beta^2 if no overflow
 
443
            occurred.  Furthermore 0 <= c3 < beta^2.
 
444
            If there was overflow and
 
445
            r[j+n]*beta+r[j+n-1] - q* * b[n-1] >= beta, i.e. c2 >= beta^2,
 
446
            the next test can be skipped.}
 
447
           While c3 > c2, {Here 0 <= c2 < c3 < beta^2}
 
448
             Put q* := q* - 1, c2 := c2 + b[n-1]*beta, c3 := c3 - b[n-2].
 
449
           If q* > 0:
 
450
             Put r := r - b * q* * beta^j. In detail:
 
451
               [r[n+j],...,r[j]] := [r[n+j],...,r[j]] - q* * [b[n-1],...,b[0]].
 
452
               hence: u:=0, for i:=0 to n-1 do
 
453
                              u := u + q* * b[i],
 
454
                              r[j+i]:=r[j+i]-(u mod beta) (+ beta, if carry),
 
455
                              u:=u div beta (+ 1, if carry in subtraction)
 
456
                      r[n+j]:=r[n+j]-u.
 
457
               {Since always u = (q* * [b[i-1],...,b[0]] div beta^i) + 1
 
458
                               < q* + 1 <= beta,
 
459
                the carry u does not overflow.}
 
460
             If a negative carry occurs, put q* := q* - 1
 
461
               and [r[n+j],...,r[j]] := [r[n+j],...,r[j]] + [0,b[n-1],...,b[0]].
 
462
         Set q[j] := q*.
 
463
       Normalise [q[m-n],..,q[0]]; this yields the quotient q.
 
464
       Shift [r[n-1],...,r[0]] right by s bits and normalise; this yields the
 
465
       rest r.
 
466
       The room for q[j] can be allocated at the memory location of r[n+j].
 
467
     Finally, round-to-even:
 
468
       Shift r left by 1 bit.
 
469
       If r > b or if r = b and q[0] is odd, q := q+1.
 
470
   */
 
471
  const mp_limb_t *a_ptr = a.limbs;
 
472
  size_t a_len = a.nlimbs;
 
473
  const mp_limb_t *b_ptr = b.limbs;
 
474
  size_t b_len = b.nlimbs;
 
475
  mp_limb_t *roomptr;
 
476
  mp_limb_t *tmp_roomptr = NULL;
 
477
  mp_limb_t *q_ptr;
 
478
  size_t q_len;
 
479
  mp_limb_t *r_ptr;
 
480
  size_t r_len;
 
481
 
 
482
  /* Allocate room for a_len+2 digits.
 
483
     (Need a_len+1 digits for the real division and 1 more digit for the
 
484
     final rounding of q.)  */
 
485
  roomptr = (mp_limb_t *) malloc ((a_len + 2) * sizeof (mp_limb_t));
 
486
  if (roomptr == NULL)
 
487
    return NULL;
 
488
 
 
489
  /* Normalise a.  */
 
490
  while (a_len > 0 && a_ptr[a_len - 1] == 0)
 
491
    a_len--;
 
492
 
 
493
  /* Normalise b.  */
 
494
  for (;;)
 
495
    {
 
496
      if (b_len == 0)
 
497
        /* Division by zero.  */
 
498
        abort ();
 
499
      if (b_ptr[b_len - 1] == 0)
 
500
        b_len--;
 
501
      else
 
502
        break;
 
503
    }
 
504
 
 
505
  /* Here m = a_len >= 0 and n = b_len > 0.  */
 
506
 
 
507
  if (a_len < b_len)
 
508
    {
 
509
      /* m<n: trivial case.  q=0, r := copy of a.  */
 
510
      r_ptr = roomptr;
 
511
      r_len = a_len;
 
512
      memcpy (r_ptr, a_ptr, a_len * sizeof (mp_limb_t));
 
513
      q_ptr = roomptr + a_len;
 
514
      q_len = 0;
 
515
    }
 
516
  else if (b_len == 1)
 
517
    {
 
518
      /* n=1: single precision division.
 
519
         beta^(m-1) <= a < beta^m  ==>  beta^(m-2) <= a/b < beta^m  */
 
520
      r_ptr = roomptr;
 
521
      q_ptr = roomptr + 1;
 
522
      {
 
523
        mp_limb_t den = b_ptr[0];
 
524
        mp_limb_t remainder = 0;
 
525
        const mp_limb_t *sourceptr = a_ptr + a_len;
 
526
        mp_limb_t *destptr = q_ptr + a_len;
 
527
        size_t count;
 
528
        for (count = a_len; count > 0; count--)
 
529
          {
 
530
            mp_twolimb_t num =
 
531
              ((mp_twolimb_t) remainder << GMP_LIMB_BITS) | *--sourceptr;
 
532
            *--destptr = num / den;
 
533
            remainder = num % den;
 
534
          }
 
535
        /* Normalise and store r.  */
 
536
        if (remainder > 0)
 
537
          {
 
538
            r_ptr[0] = remainder;
 
539
            r_len = 1;
 
540
          }
 
541
        else
 
542
          r_len = 0;
 
543
        /* Normalise q.  */
 
544
        q_len = a_len;
 
545
        if (q_ptr[q_len - 1] == 0)
 
546
          q_len--;
 
547
      }
 
548
    }
 
549
  else
 
550
    {
 
551
      /* n>1: multiple precision division.
 
552
         beta^(m-1) <= a < beta^m, beta^(n-1) <= b < beta^n  ==>
 
553
         beta^(m-n-1) <= a/b < beta^(m-n+1).  */
 
554
      /* Determine s.  */
 
555
      size_t s;
 
556
      {
 
557
        mp_limb_t msd = b_ptr[b_len - 1]; /* = b[n-1], > 0 */
 
558
        s = 31;
 
559
        if (msd >= 0x10000)
 
560
          {
 
561
            msd = msd >> 16;
 
562
            s -= 16;
 
563
          }
 
564
        if (msd >= 0x100)
 
565
          {
 
566
            msd = msd >> 8;
 
567
            s -= 8;
 
568
          }
 
569
        if (msd >= 0x10)
 
570
          {
 
571
            msd = msd >> 4;
 
572
            s -= 4;
 
573
          }
 
574
        if (msd >= 0x4)
 
575
          {
 
576
            msd = msd >> 2;
 
577
            s -= 2;
 
578
          }
 
579
        if (msd >= 0x2)
 
580
          {
 
581
            msd = msd >> 1;
 
582
            s -= 1;
 
583
          }
 
584
      }
 
585
      /* 0 <= s < GMP_LIMB_BITS.
 
586
         Copy b, shifting it left by s bits.  */
 
587
      if (s > 0)
 
588
        {
 
589
          tmp_roomptr = (mp_limb_t *) malloc (b_len * sizeof (mp_limb_t));
 
590
          if (tmp_roomptr == NULL)
 
591
            {
 
592
              free (roomptr);
 
593
              return NULL;
 
594
            }
 
595
          {
 
596
            const mp_limb_t *sourceptr = b_ptr;
 
597
            mp_limb_t *destptr = tmp_roomptr;
 
598
            mp_twolimb_t accu = 0;
 
599
            size_t count;
 
600
            for (count = b_len; count > 0; count--)
 
601
              {
 
602
                accu += (mp_twolimb_t) *sourceptr++ << s;
 
603
                *destptr++ = (mp_limb_t) accu;
 
604
                accu = accu >> GMP_LIMB_BITS;
 
605
              }
 
606
            /* accu must be zero, since that was how s was determined.  */
 
607
            if (accu != 0)
 
608
              abort ();
 
609
          }
 
610
          b_ptr = tmp_roomptr;
 
611
        }
 
612
      /* Copy a, shifting it left by s bits, yields r.
 
613
         Memory layout:
 
614
         At the beginning: r = roomptr[0..a_len],
 
615
         at the end: r = roomptr[0..b_len-1], q = roomptr[b_len..a_len]  */
 
616
      r_ptr = roomptr;
 
617
      if (s == 0)
 
618
        {
 
619
          memcpy (r_ptr, a_ptr, a_len * sizeof (mp_limb_t));
 
620
          r_ptr[a_len] = 0;
 
621
        }
 
622
      else
 
623
        {
 
624
          const mp_limb_t *sourceptr = a_ptr;
 
625
          mp_limb_t *destptr = r_ptr;
 
626
          mp_twolimb_t accu = 0;
 
627
          size_t count;
 
628
          for (count = a_len; count > 0; count--)
 
629
            {
 
630
              accu += (mp_twolimb_t) *sourceptr++ << s;
 
631
              *destptr++ = (mp_limb_t) accu;
 
632
              accu = accu >> GMP_LIMB_BITS;
 
633
            }
 
634
          *destptr++ = (mp_limb_t) accu;
 
635
        }
 
636
      q_ptr = roomptr + b_len;
 
637
      q_len = a_len - b_len + 1; /* q will have m-n+1 limbs */
 
638
      {
 
639
        size_t j = a_len - b_len; /* m-n */
 
640
        mp_limb_t b_msd = b_ptr[b_len - 1]; /* b[n-1] */
 
641
        mp_limb_t b_2msd = b_ptr[b_len - 2]; /* b[n-2] */
 
642
        mp_twolimb_t b_msdd = /* b[n-1]*beta+b[n-2] */
 
643
          ((mp_twolimb_t) b_msd << GMP_LIMB_BITS) | b_2msd;
 
644
        /* Division loop, traversed m-n+1 times.
 
645
           j counts down, b is unchanged, beta/2 <= b[n-1] < beta.  */
 
646
        for (;;)
 
647
          {
 
648
            mp_limb_t q_star;
 
649
            mp_limb_t c1;
 
650
            if (r_ptr[j + b_len] < b_msd) /* r[j+n] < b[n-1] ? */
 
651
              {
 
652
                /* Divide r[j+n]*beta+r[j+n-1] by b[n-1], no overflow.  */
 
653
                mp_twolimb_t num =
 
654
                  ((mp_twolimb_t) r_ptr[j + b_len] << GMP_LIMB_BITS)
 
655
                  | r_ptr[j + b_len - 1];
 
656
                q_star = num / b_msd;
 
657
                c1 = num % b_msd;
 
658
              }
 
659
            else
 
660
              {
 
661
                /* Overflow, hence r[j+n]*beta+r[j+n-1] >= beta*b[n-1].  */
 
662
                q_star = (mp_limb_t)~(mp_limb_t)0; /* q* = beta-1 */
 
663
                /* Test whether r[j+n]*beta+r[j+n-1] - (beta-1)*b[n-1] >= beta
 
664
                   <==> r[j+n]*beta+r[j+n-1] + b[n-1] >= beta*b[n-1]+beta
 
665
                   <==> b[n-1] < floor((r[j+n]*beta+r[j+n-1]+b[n-1])/beta)
 
666
                        {<= beta !}.
 
667
                   If yes, jump directly to the subtraction loop.
 
668
                   (Otherwise, r[j+n]*beta+r[j+n-1] - (beta-1)*b[n-1] < beta
 
669
                    <==> floor((r[j+n]*beta+r[j+n-1]+b[n-1])/beta) = b[n-1] ) */
 
670
                if (r_ptr[j + b_len] > b_msd
 
671
                    || (c1 = r_ptr[j + b_len - 1] + b_msd) < b_msd)
 
672
                  /* r[j+n] >= b[n-1]+1 or
 
673
                     r[j+n] = b[n-1] and the addition r[j+n-1]+b[n-1] gives a
 
674
                     carry.  */
 
675
                  goto subtract;
 
676
              }
 
677
            /* q_star = q*,
 
678
               c1 = (r[j+n]*beta+r[j+n-1]) - q* * b[n-1] (>=0, <beta).  */
 
679
            {
 
680
              mp_twolimb_t c2 = /* c1*beta+r[j+n-2] */
 
681
                ((mp_twolimb_t) c1 << GMP_LIMB_BITS) | r_ptr[j + b_len - 2];
 
682
              mp_twolimb_t c3 = /* b[n-2] * q* */
 
683
                (mp_twolimb_t) b_2msd * (mp_twolimb_t) q_star;
 
684
              /* While c2 < c3, increase c2 and decrease c3.
 
685
                 Consider c3-c2.  While it is > 0, decrease it by
 
686
                 b[n-1]*beta+b[n-2].  Because of b[n-1]*beta+b[n-2] >= beta^2/2
 
687
                 this can happen only twice.  */
 
688
              if (c3 > c2)
 
689
                {
 
690
                  q_star = q_star - 1; /* q* := q* - 1 */
 
691
                  if (c3 - c2 > b_msdd)
 
692
                    q_star = q_star - 1; /* q* := q* - 1 */
 
693
                }
 
694
            }
 
695
            if (q_star > 0)
 
696
              subtract:
 
697
              {
 
698
                /* Subtract r := r - b * q* * beta^j.  */
 
699
                mp_limb_t cr;
 
700
                {
 
701
                  const mp_limb_t *sourceptr = b_ptr;
 
702
                  mp_limb_t *destptr = r_ptr + j;
 
703
                  mp_twolimb_t carry = 0;
 
704
                  size_t count;
 
705
                  for (count = b_len; count > 0; count--)
 
706
                    {
 
707
                      /* Here 0 <= carry <= q*.  */
 
708
                      carry =
 
709
                        carry
 
710
                        + (mp_twolimb_t) q_star * (mp_twolimb_t) *sourceptr++
 
711
                        + (mp_limb_t) ~(*destptr);
 
712
                      /* Here 0 <= carry <= beta*q* + beta-1.  */
 
713
                      *destptr++ = ~(mp_limb_t) carry;
 
714
                      carry = carry >> GMP_LIMB_BITS; /* <= q* */
 
715
                    }
 
716
                  cr = (mp_limb_t) carry;
 
717
                }
 
718
                /* Subtract cr from r_ptr[j + b_len], then forget about
 
719
                   r_ptr[j + b_len].  */
 
720
                if (cr > r_ptr[j + b_len])
 
721
                  {
 
722
                    /* Subtraction gave a carry.  */
 
723
                    q_star = q_star - 1; /* q* := q* - 1 */
 
724
                    /* Add b back.  */
 
725
                    {
 
726
                      const mp_limb_t *sourceptr = b_ptr;
 
727
                      mp_limb_t *destptr = r_ptr + j;
 
728
                      mp_limb_t carry = 0;
 
729
                      size_t count;
 
730
                      for (count = b_len; count > 0; count--)
 
731
                        {
 
732
                          mp_limb_t source1 = *sourceptr++;
 
733
                          mp_limb_t source2 = *destptr;
 
734
                          *destptr++ = source1 + source2 + carry;
 
735
                          carry =
 
736
                            (carry
 
737
                             ? source1 >= (mp_limb_t) ~source2
 
738
                             : source1 > (mp_limb_t) ~source2);
 
739
                        }
 
740
                    }
 
741
                    /* Forget about the carry and about r[j+n].  */
 
742
                  }
 
743
              }
 
744
            /* q* is determined.  Store it as q[j].  */
 
745
            q_ptr[j] = q_star;
 
746
            if (j == 0)
 
747
              break;
 
748
            j--;
 
749
          }
 
750
      }
 
751
      r_len = b_len;
 
752
      /* Normalise q.  */
 
753
      if (q_ptr[q_len - 1] == 0)
 
754
        q_len--;
 
755
# if 0 /* Not needed here, since we need r only to compare it with b/2, and
 
756
          b is shifted left by s bits.  */
 
757
      /* Shift r right by s bits.  */
 
758
      if (s > 0)
 
759
        {
 
760
          mp_limb_t ptr = r_ptr + r_len;
 
761
          mp_twolimb_t accu = 0;
 
762
          size_t count;
 
763
          for (count = r_len; count > 0; count--)
 
764
            {
 
765
              accu = (mp_twolimb_t) (mp_limb_t) accu << GMP_LIMB_BITS;
 
766
              accu += (mp_twolimb_t) *--ptr << (GMP_LIMB_BITS - s);
 
767
              *ptr = (mp_limb_t) (accu >> GMP_LIMB_BITS);
 
768
            }
 
769
        }
 
770
# endif
 
771
      /* Normalise r.  */
 
772
      while (r_len > 0 && r_ptr[r_len - 1] == 0)
 
773
        r_len--;
 
774
    }
 
775
  /* Compare r << 1 with b.  */
 
776
  if (r_len > b_len)
 
777
    goto increment_q;
 
778
  {
 
779
    size_t i;
 
780
    for (i = b_len;;)
 
781
      {
 
782
        mp_limb_t r_i =
 
783
          (i <= r_len && i > 0 ? r_ptr[i - 1] >> (GMP_LIMB_BITS - 1) : 0)
 
784
          | (i < r_len ? r_ptr[i] << 1 : 0);
 
785
        mp_limb_t b_i = (i < b_len ? b_ptr[i] : 0);
 
786
        if (r_i > b_i)
 
787
          goto increment_q;
 
788
        if (r_i < b_i)
 
789
          goto keep_q;
 
790
        if (i == 0)
 
791
          break;
 
792
        i--;
 
793
      }
 
794
  }
 
795
  if (q_len > 0 && ((q_ptr[0] & 1) != 0))
 
796
    /* q is odd.  */
 
797
    increment_q:
 
798
    {
 
799
      size_t i;
 
800
      for (i = 0; i < q_len; i++)
 
801
        if (++(q_ptr[i]) != 0)
 
802
          goto keep_q;
 
803
      q_ptr[q_len++] = 1;
 
804
    }
 
805
  keep_q:
 
806
  if (tmp_roomptr != NULL)
 
807
    free (tmp_roomptr);
 
808
  q->limbs = q_ptr;
 
809
  q->nlimbs = q_len;
 
810
  return roomptr;
 
811
}
 
812
 
 
813
/* Convert a bignum a >= 0, multiplied with 10^extra_zeroes, to decimal
 
814
   representation.
 
815
   Destroys the contents of a.
 
816
   Return the allocated memory - containing the decimal digits in low-to-high
 
817
   order, terminated with a NUL character - in case of success, NULL in case
 
818
   of memory allocation failure.  */
 
819
static char *
 
820
convert_to_decimal (mpn_t a, size_t extra_zeroes)
 
821
{
 
822
  mp_limb_t *a_ptr = a.limbs;
 
823
  size_t a_len = a.nlimbs;
 
824
  /* 0.03345 is slightly larger than log(2)/(9*log(10)).  */
 
825
  size_t c_len = 9 * ((size_t)(a_len * (GMP_LIMB_BITS * 0.03345f)) + 1);
 
826
  char *c_ptr = (char *) malloc (xsum (c_len, extra_zeroes));
 
827
  if (c_ptr != NULL)
 
828
    {
 
829
      char *d_ptr = c_ptr;
 
830
      for (; extra_zeroes > 0; extra_zeroes--)
 
831
        *d_ptr++ = '0';
 
832
      while (a_len > 0)
 
833
        {
 
834
          /* Divide a by 10^9, in-place.  */
 
835
          mp_limb_t remainder = 0;
 
836
          mp_limb_t *ptr = a_ptr + a_len;
 
837
          size_t count;
 
838
          for (count = a_len; count > 0; count--)
 
839
            {
 
840
              mp_twolimb_t num =
 
841
                ((mp_twolimb_t) remainder << GMP_LIMB_BITS) | *--ptr;
 
842
              *ptr = num / 1000000000;
 
843
              remainder = num % 1000000000;
 
844
            }
 
845
          /* Store the remainder as 9 decimal digits.  */
 
846
          for (count = 9; count > 0; count--)
 
847
            {
 
848
              *d_ptr++ = '0' + (remainder % 10);
 
849
              remainder = remainder / 10;
 
850
            }
 
851
          /* Normalize a.  */
 
852
          if (a_ptr[a_len - 1] == 0)
 
853
            a_len--;
 
854
        }
 
855
      /* Remove leading zeroes.  */
 
856
      while (d_ptr > c_ptr && d_ptr[-1] == '0')
 
857
        d_ptr--;
 
858
      /* But keep at least one zero.  */
 
859
      if (d_ptr == c_ptr)
 
860
        *d_ptr++ = '0';
 
861
      /* Terminate the string.  */
 
862
      *d_ptr = '\0';
 
863
    }
 
864
  return c_ptr;
 
865
}
 
866
 
 
867
# if NEED_PRINTF_LONG_DOUBLE
 
868
 
 
869
/* Assuming x is finite and >= 0:
 
870
   write x as x = 2^e * m, where m is a bignum.
 
871
   Return the allocated memory in case of success, NULL in case of memory
 
872
   allocation failure.  */
 
873
static void *
 
874
decode_long_double (long double x, int *ep, mpn_t *mp)
 
875
{
 
876
  mpn_t m;
 
877
  int exp;
 
878
  long double y;
 
879
  size_t i;
 
880
 
 
881
  /* Allocate memory for result.  */
 
882
  m.nlimbs = (LDBL_MANT_BIT + GMP_LIMB_BITS - 1) / GMP_LIMB_BITS;
 
883
  m.limbs = (mp_limb_t *) malloc (m.nlimbs * sizeof (mp_limb_t));
 
884
  if (m.limbs == NULL)
 
885
    return NULL;
 
886
  /* Split into exponential part and mantissa.  */
 
887
  y = frexpl (x, &exp);
 
888
  if (!(y >= 0.0L && y < 1.0L))
 
889
    abort ();
 
890
  /* x = 2^exp * y = 2^(exp - LDBL_MANT_BIT) * (y * LDBL_MANT_BIT), and the
 
891
     latter is an integer.  */
 
892
  /* Convert the mantissa (y * LDBL_MANT_BIT) to a sequence of limbs.
 
893
     I'm not sure whether it's safe to cast a 'long double' value between
 
894
     2^31 and 2^32 to 'unsigned int', therefore play safe and cast only
 
895
     'long double' values between 0 and 2^16 (to 'unsigned int' or 'int',
 
896
     doesn't matter).  */
 
897
#  if (LDBL_MANT_BIT % GMP_LIMB_BITS) != 0
 
898
#   if (LDBL_MANT_BIT % GMP_LIMB_BITS) > GMP_LIMB_BITS / 2
 
899
    {
 
900
      mp_limb_t hi, lo;
 
901
      y *= (mp_limb_t) 1 << (LDBL_MANT_BIT % (GMP_LIMB_BITS / 2));
 
902
      hi = (int) y;
 
903
      y -= hi;
 
904
      if (!(y >= 0.0L && y < 1.0L))
 
905
        abort ();
 
906
      y *= (mp_limb_t) 1 << (GMP_LIMB_BITS / 2);
 
907
      lo = (int) y;
 
908
      y -= lo;
 
909
      if (!(y >= 0.0L && y < 1.0L))
 
910
        abort ();
 
911
      m.limbs[LDBL_MANT_BIT / GMP_LIMB_BITS] = (hi << (GMP_LIMB_BITS / 2)) | lo;
 
912
    }
 
913
#   else
 
914
    {
 
915
      mp_limb_t d;
 
916
      y *= (mp_limb_t) 1 << (LDBL_MANT_BIT % GMP_LIMB_BITS);
 
917
      d = (int) y;
 
918
      y -= d;
 
919
      if (!(y >= 0.0L && y < 1.0L))
 
920
        abort ();
 
921
      m.limbs[LDBL_MANT_BIT / GMP_LIMB_BITS] = d;
 
922
    }
 
923
#   endif
 
924
#  endif
 
925
  for (i = LDBL_MANT_BIT / GMP_LIMB_BITS; i > 0; )
 
926
    {
 
927
      mp_limb_t hi, lo;
 
928
      y *= (mp_limb_t) 1 << (GMP_LIMB_BITS / 2);
 
929
      hi = (int) y;
 
930
      y -= hi;
 
931
      if (!(y >= 0.0L && y < 1.0L))
 
932
        abort ();
 
933
      y *= (mp_limb_t) 1 << (GMP_LIMB_BITS / 2);
 
934
      lo = (int) y;
 
935
      y -= lo;
 
936
      if (!(y >= 0.0L && y < 1.0L))
 
937
        abort ();
 
938
      m.limbs[--i] = (hi << (GMP_LIMB_BITS / 2)) | lo;
 
939
    }
 
940
#  if 0 /* On FreeBSD 6.1/x86, 'long double' numbers sometimes have excess
 
941
           precision.  */
 
942
  if (!(y == 0.0L))
 
943
    abort ();
 
944
#  endif
 
945
  /* Normalise.  */
 
946
  while (m.nlimbs > 0 && m.limbs[m.nlimbs - 1] == 0)
 
947
    m.nlimbs--;
 
948
  *mp = m;
 
949
  *ep = exp - LDBL_MANT_BIT;
 
950
  return m.limbs;
 
951
}
 
952
 
 
953
# endif
 
954
 
 
955
# if NEED_PRINTF_DOUBLE
 
956
 
 
957
/* Assuming x is finite and >= 0:
 
958
   write x as x = 2^e * m, where m is a bignum.
 
959
   Return the allocated memory in case of success, NULL in case of memory
 
960
   allocation failure.  */
 
961
static void *
 
962
decode_double (double x, int *ep, mpn_t *mp)
 
963
{
 
964
  mpn_t m;
 
965
  int exp;
 
966
  double y;
 
967
  size_t i;
 
968
 
 
969
  /* Allocate memory for result.  */
 
970
  m.nlimbs = (DBL_MANT_BIT + GMP_LIMB_BITS - 1) / GMP_LIMB_BITS;
 
971
  m.limbs = (mp_limb_t *) malloc (m.nlimbs * sizeof (mp_limb_t));
 
972
  if (m.limbs == NULL)
 
973
    return NULL;
 
974
  /* Split into exponential part and mantissa.  */
 
975
  y = frexp (x, &exp);
 
976
  if (!(y >= 0.0 && y < 1.0))
 
977
    abort ();
 
978
  /* x = 2^exp * y = 2^(exp - DBL_MANT_BIT) * (y * DBL_MANT_BIT), and the
 
979
     latter is an integer.  */
 
980
  /* Convert the mantissa (y * DBL_MANT_BIT) to a sequence of limbs.
 
981
     I'm not sure whether it's safe to cast a 'double' value between
 
982
     2^31 and 2^32 to 'unsigned int', therefore play safe and cast only
 
983
     'double' values between 0 and 2^16 (to 'unsigned int' or 'int',
 
984
     doesn't matter).  */
 
985
#  if (DBL_MANT_BIT % GMP_LIMB_BITS) != 0
 
986
#   if (DBL_MANT_BIT % GMP_LIMB_BITS) > GMP_LIMB_BITS / 2
 
987
    {
 
988
      mp_limb_t hi, lo;
 
989
      y *= (mp_limb_t) 1 << (DBL_MANT_BIT % (GMP_LIMB_BITS / 2));
 
990
      hi = (int) y;
 
991
      y -= hi;
 
992
      if (!(y >= 0.0 && y < 1.0))
 
993
        abort ();
 
994
      y *= (mp_limb_t) 1 << (GMP_LIMB_BITS / 2);
 
995
      lo = (int) y;
 
996
      y -= lo;
 
997
      if (!(y >= 0.0 && y < 1.0))
 
998
        abort ();
 
999
      m.limbs[DBL_MANT_BIT / GMP_LIMB_BITS] = (hi << (GMP_LIMB_BITS / 2)) | lo;
 
1000
    }
 
1001
#   else
 
1002
    {
 
1003
      mp_limb_t d;
 
1004
      y *= (mp_limb_t) 1 << (DBL_MANT_BIT % GMP_LIMB_BITS);
 
1005
      d = (int) y;
 
1006
      y -= d;
 
1007
      if (!(y >= 0.0 && y < 1.0))
 
1008
        abort ();
 
1009
      m.limbs[DBL_MANT_BIT / GMP_LIMB_BITS] = d;
 
1010
    }
 
1011
#   endif
 
1012
#  endif
 
1013
  for (i = DBL_MANT_BIT / GMP_LIMB_BITS; i > 0; )
 
1014
    {
 
1015
      mp_limb_t hi, lo;
 
1016
      y *= (mp_limb_t) 1 << (GMP_LIMB_BITS / 2);
 
1017
      hi = (int) y;
 
1018
      y -= hi;
 
1019
      if (!(y >= 0.0 && y < 1.0))
 
1020
        abort ();
 
1021
      y *= (mp_limb_t) 1 << (GMP_LIMB_BITS / 2);
 
1022
      lo = (int) y;
 
1023
      y -= lo;
 
1024
      if (!(y >= 0.0 && y < 1.0))
 
1025
        abort ();
 
1026
      m.limbs[--i] = (hi << (GMP_LIMB_BITS / 2)) | lo;
 
1027
    }
 
1028
  if (!(y == 0.0))
 
1029
    abort ();
 
1030
  /* Normalise.  */
 
1031
  while (m.nlimbs > 0 && m.limbs[m.nlimbs - 1] == 0)
 
1032
    m.nlimbs--;
 
1033
  *mp = m;
 
1034
  *ep = exp - DBL_MANT_BIT;
 
1035
  return m.limbs;
 
1036
}
 
1037
 
 
1038
# endif
 
1039
 
 
1040
/* Assuming x = 2^e * m is finite and >= 0, and n is an integer:
 
1041
   Returns the decimal representation of round (x * 10^n).
 
1042
   Return the allocated memory - containing the decimal digits in low-to-high
 
1043
   order, terminated with a NUL character - in case of success, NULL in case
 
1044
   of memory allocation failure.  */
 
1045
static char *
 
1046
scale10_round_decimal_decoded (int e, mpn_t m, void *memory, int n)
 
1047
{
 
1048
  int s;
 
1049
  size_t extra_zeroes;
 
1050
  unsigned int abs_n;
 
1051
  unsigned int abs_s;
 
1052
  mp_limb_t *pow5_ptr;
 
1053
  size_t pow5_len;
 
1054
  unsigned int s_limbs;
 
1055
  unsigned int s_bits;
 
1056
  mpn_t pow5;
 
1057
  mpn_t z;
 
1058
  void *z_memory;
 
1059
  char *digits;
 
1060
 
 
1061
  if (memory == NULL)
 
1062
    return NULL;
 
1063
  /* x = 2^e * m, hence
 
1064
     y = round (2^e * 10^n * m) = round (2^(e+n) * 5^n * m)
 
1065
       = round (2^s * 5^n * m).  */
 
1066
  s = e + n;
 
1067
  extra_zeroes = 0;
 
1068
  /* Factor out a common power of 10 if possible.  */
 
1069
  if (s > 0 && n > 0)
 
1070
    {
 
1071
      extra_zeroes = (s < n ? s : n);
 
1072
      s -= extra_zeroes;
 
1073
      n -= extra_zeroes;
 
1074
    }
 
1075
  /* Here y = round (2^s * 5^n * m) * 10^extra_zeroes.
 
1076
     Before converting to decimal, we need to compute
 
1077
     z = round (2^s * 5^n * m).  */
 
1078
  /* Compute 5^|n|, possibly shifted by |s| bits if n and s have the same
 
1079
     sign.  2.322 is slightly larger than log(5)/log(2).  */
 
1080
  abs_n = (n >= 0 ? n : -n);
 
1081
  abs_s = (s >= 0 ? s : -s);
 
1082
  pow5_ptr = (mp_limb_t *) malloc (((int)(abs_n * (2.322f / GMP_LIMB_BITS)) + 1
 
1083
                                    + abs_s / GMP_LIMB_BITS + 1)
 
1084
                                   * sizeof (mp_limb_t));
 
1085
  if (pow5_ptr == NULL)
 
1086
    {
 
1087
      free (memory);
 
1088
      return NULL;
 
1089
    }
 
1090
  /* Initialize with 1.  */
 
1091
  pow5_ptr[0] = 1;
 
1092
  pow5_len = 1;
 
1093
  /* Multiply with 5^|n|.  */
 
1094
  if (abs_n > 0)
 
1095
    {
 
1096
      static mp_limb_t const small_pow5[13 + 1] =
 
1097
        {
 
1098
          1, 5, 25, 125, 625, 3125, 15625, 78125, 390625, 1953125, 9765625,
 
1099
          48828125, 244140625, 1220703125
 
1100
        };
 
1101
      unsigned int n13;
 
1102
      for (n13 = 0; n13 <= abs_n; n13 += 13)
 
1103
        {
 
1104
          mp_limb_t digit1 = small_pow5[n13 + 13 <= abs_n ? 13 : abs_n - n13];
 
1105
          size_t j;
 
1106
          mp_twolimb_t carry = 0;
 
1107
          for (j = 0; j < pow5_len; j++)
 
1108
            {
 
1109
              mp_limb_t digit2 = pow5_ptr[j];
 
1110
              carry += (mp_twolimb_t) digit1 * (mp_twolimb_t) digit2;
 
1111
              pow5_ptr[j] = (mp_limb_t) carry;
 
1112
              carry = carry >> GMP_LIMB_BITS;
 
1113
            }
 
1114
          if (carry > 0)
 
1115
            pow5_ptr[pow5_len++] = (mp_limb_t) carry;
 
1116
        }
 
1117
    }
 
1118
  s_limbs = abs_s / GMP_LIMB_BITS;
 
1119
  s_bits = abs_s % GMP_LIMB_BITS;
 
1120
  if (n >= 0 ? s >= 0 : s <= 0)
 
1121
    {
 
1122
      /* Multiply with 2^|s|.  */
 
1123
      if (s_bits > 0)
 
1124
        {
 
1125
          mp_limb_t *ptr = pow5_ptr;
 
1126
          mp_twolimb_t accu = 0;
 
1127
          size_t count;
 
1128
          for (count = pow5_len; count > 0; count--)
 
1129
            {
 
1130
              accu += (mp_twolimb_t) *ptr << s_bits;
 
1131
              *ptr++ = (mp_limb_t) accu;
 
1132
              accu = accu >> GMP_LIMB_BITS;
 
1133
            }
 
1134
          if (accu > 0)
 
1135
            {
 
1136
              *ptr = (mp_limb_t) accu;
 
1137
              pow5_len++;
 
1138
            }
 
1139
        }
 
1140
      if (s_limbs > 0)
 
1141
        {
 
1142
          size_t count;
 
1143
          for (count = pow5_len; count > 0;)
 
1144
            {
 
1145
              count--;
 
1146
              pow5_ptr[s_limbs + count] = pow5_ptr[count];
 
1147
            }
 
1148
          for (count = s_limbs; count > 0;)
 
1149
            {
 
1150
              count--;
 
1151
              pow5_ptr[count] = 0;
 
1152
            }
 
1153
          pow5_len += s_limbs;
 
1154
        }
 
1155
      pow5.limbs = pow5_ptr;
 
1156
      pow5.nlimbs = pow5_len;
 
1157
      if (n >= 0)
 
1158
        {
 
1159
          /* Multiply m with pow5.  No division needed.  */
 
1160
          z_memory = multiply (m, pow5, &z);
 
1161
        }
 
1162
      else
 
1163
        {
 
1164
          /* Divide m by pow5 and round.  */
 
1165
          z_memory = divide (m, pow5, &z);
 
1166
        }
 
1167
    }
 
1168
  else
 
1169
    {
 
1170
      pow5.limbs = pow5_ptr;
 
1171
      pow5.nlimbs = pow5_len;
 
1172
      if (n >= 0)
 
1173
        {
 
1174
          /* n >= 0, s < 0.
 
1175
             Multiply m with pow5, then divide by 2^|s|.  */
 
1176
          mpn_t numerator;
 
1177
          mpn_t denominator;
 
1178
          void *tmp_memory;
 
1179
          tmp_memory = multiply (m, pow5, &numerator);
 
1180
          if (tmp_memory == NULL)
 
1181
            {
 
1182
              free (pow5_ptr);
 
1183
              free (memory);
 
1184
              return NULL;
 
1185
            }
 
1186
          /* Construct 2^|s|.  */
 
1187
          {
 
1188
            mp_limb_t *ptr = pow5_ptr + pow5_len;
 
1189
            size_t i;
 
1190
            for (i = 0; i < s_limbs; i++)
 
1191
              ptr[i] = 0;
 
1192
            ptr[s_limbs] = (mp_limb_t) 1 << s_bits;
 
1193
            denominator.limbs = ptr;
 
1194
            denominator.nlimbs = s_limbs + 1;
 
1195
          }
 
1196
          z_memory = divide (numerator, denominator, &z);
 
1197
          free (tmp_memory);
 
1198
        }
 
1199
      else
 
1200
        {
 
1201
          /* n < 0, s > 0.
 
1202
             Multiply m with 2^s, then divide by pow5.  */
 
1203
          mpn_t numerator;
 
1204
          mp_limb_t *num_ptr;
 
1205
          num_ptr = (mp_limb_t *) malloc ((m.nlimbs + s_limbs + 1)
 
1206
                                          * sizeof (mp_limb_t));
 
1207
          if (num_ptr == NULL)
 
1208
            {
 
1209
              free (pow5_ptr);
 
1210
              free (memory);
 
1211
              return NULL;
 
1212
            }
 
1213
          {
 
1214
            mp_limb_t *destptr = num_ptr;
 
1215
            {
 
1216
              size_t i;
 
1217
              for (i = 0; i < s_limbs; i++)
 
1218
                *destptr++ = 0;
 
1219
            }
 
1220
            if (s_bits > 0)
 
1221
              {
 
1222
                const mp_limb_t *sourceptr = m.limbs;
 
1223
                mp_twolimb_t accu = 0;
 
1224
                size_t count;
 
1225
                for (count = m.nlimbs; count > 0; count--)
 
1226
                  {
 
1227
                    accu += (mp_twolimb_t) *sourceptr++ << s_bits;
 
1228
                    *destptr++ = (mp_limb_t) accu;
 
1229
                    accu = accu >> GMP_LIMB_BITS;
 
1230
                  }
 
1231
                if (accu > 0)
 
1232
                  *destptr++ = (mp_limb_t) accu;
 
1233
              }
 
1234
            else
 
1235
              {
 
1236
                const mp_limb_t *sourceptr = m.limbs;
 
1237
                size_t count;
 
1238
                for (count = m.nlimbs; count > 0; count--)
 
1239
                  *destptr++ = *sourceptr++;
 
1240
              }
 
1241
            numerator.limbs = num_ptr;
 
1242
            numerator.nlimbs = destptr - num_ptr;
 
1243
          }
 
1244
          z_memory = divide (numerator, pow5, &z);
 
1245
          free (num_ptr);
 
1246
        }
 
1247
    }
 
1248
  free (pow5_ptr);
 
1249
  free (memory);
 
1250
 
 
1251
  /* Here y = round (x * 10^n) = z * 10^extra_zeroes.  */
 
1252
 
 
1253
  if (z_memory == NULL)
 
1254
    return NULL;
 
1255
  digits = convert_to_decimal (z, extra_zeroes);
 
1256
  free (z_memory);
 
1257
  return digits;
 
1258
}
 
1259
 
 
1260
# if NEED_PRINTF_LONG_DOUBLE
 
1261
 
 
1262
/* Assuming x is finite and >= 0, and n is an integer:
 
1263
   Returns the decimal representation of round (x * 10^n).
 
1264
   Return the allocated memory - containing the decimal digits in low-to-high
 
1265
   order, terminated with a NUL character - in case of success, NULL in case
 
1266
   of memory allocation failure.  */
 
1267
static char *
 
1268
scale10_round_decimal_long_double (long double x, int n)
 
1269
{
 
1270
  int e IF_LINT(= 0);
 
1271
  mpn_t m;
 
1272
  void *memory = decode_long_double (x, &e, &m);
 
1273
  return scale10_round_decimal_decoded (e, m, memory, n);
 
1274
}
 
1275
 
 
1276
# endif
 
1277
 
 
1278
# if NEED_PRINTF_DOUBLE
 
1279
 
 
1280
/* Assuming x is finite and >= 0, and n is an integer:
 
1281
   Returns the decimal representation of round (x * 10^n).
 
1282
   Return the allocated memory - containing the decimal digits in low-to-high
 
1283
   order, terminated with a NUL character - in case of success, NULL in case
 
1284
   of memory allocation failure.  */
 
1285
static char *
 
1286
scale10_round_decimal_double (double x, int n)
 
1287
{
 
1288
  int e IF_LINT(= 0);
 
1289
  mpn_t m;
 
1290
  void *memory = decode_double (x, &e, &m);
 
1291
  return scale10_round_decimal_decoded (e, m, memory, n);
 
1292
}
 
1293
 
 
1294
# endif
 
1295
 
 
1296
# if NEED_PRINTF_LONG_DOUBLE
 
1297
 
 
1298
/* Assuming x is finite and > 0:
 
1299
   Return an approximation for n with 10^n <= x < 10^(n+1).
 
1300
   The approximation is usually the right n, but may be off by 1 sometimes.  */
 
1301
static int
 
1302
floorlog10l (long double x)
 
1303
{
 
1304
  int exp;
 
1305
  long double y;
 
1306
  double z;
 
1307
  double l;
 
1308
 
 
1309
  /* Split into exponential part and mantissa.  */
 
1310
  y = frexpl (x, &exp);
 
1311
  if (!(y >= 0.0L && y < 1.0L))
 
1312
    abort ();
 
1313
  if (y == 0.0L)
 
1314
    return INT_MIN;
 
1315
  if (y < 0.5L)
 
1316
    {
 
1317
      while (y < (1.0L / (1 << (GMP_LIMB_BITS / 2)) / (1 << (GMP_LIMB_BITS / 2))))
 
1318
        {
 
1319
          y *= 1.0L * (1 << (GMP_LIMB_BITS / 2)) * (1 << (GMP_LIMB_BITS / 2));
 
1320
          exp -= GMP_LIMB_BITS;
 
1321
        }
 
1322
      if (y < (1.0L / (1 << 16)))
 
1323
        {
 
1324
          y *= 1.0L * (1 << 16);
 
1325
          exp -= 16;
 
1326
        }
 
1327
      if (y < (1.0L / (1 << 8)))
 
1328
        {
 
1329
          y *= 1.0L * (1 << 8);
 
1330
          exp -= 8;
 
1331
        }
 
1332
      if (y < (1.0L / (1 << 4)))
 
1333
        {
 
1334
          y *= 1.0L * (1 << 4);
 
1335
          exp -= 4;
 
1336
        }
 
1337
      if (y < (1.0L / (1 << 2)))
 
1338
        {
 
1339
          y *= 1.0L * (1 << 2);
 
1340
          exp -= 2;
 
1341
        }
 
1342
      if (y < (1.0L / (1 << 1)))
 
1343
        {
 
1344
          y *= 1.0L * (1 << 1);
 
1345
          exp -= 1;
 
1346
        }
 
1347
    }
 
1348
  if (!(y >= 0.5L && y < 1.0L))
 
1349
    abort ();
 
1350
  /* Compute an approximation for l = log2(x) = exp + log2(y).  */
 
1351
  l = exp;
 
1352
  z = y;
 
1353
  if (z < 0.70710678118654752444)
 
1354
    {
 
1355
      z *= 1.4142135623730950488;
 
1356
      l -= 0.5;
 
1357
    }
 
1358
  if (z < 0.8408964152537145431)
 
1359
    {
 
1360
      z *= 1.1892071150027210667;
 
1361
      l -= 0.25;
 
1362
    }
 
1363
  if (z < 0.91700404320467123175)
 
1364
    {
 
1365
      z *= 1.0905077326652576592;
 
1366
      l -= 0.125;
 
1367
    }
 
1368
  if (z < 0.9576032806985736469)
 
1369
    {
 
1370
      z *= 1.0442737824274138403;
 
1371
      l -= 0.0625;
 
1372
    }
 
1373
  /* Now 0.95 <= z <= 1.01.  */
 
1374
  z = 1 - z;
 
1375
  /* log2(1-z) = 1/log(2) * (- z - z^2/2 - z^3/3 - z^4/4 - ...)
 
1376
     Four terms are enough to get an approximation with error < 10^-7.  */
 
1377
  l -= 1.4426950408889634074 * z * (1.0 + z * (0.5 + z * ((1.0 / 3) + z * 0.25)));
 
1378
  /* Finally multiply with log(2)/log(10), yields an approximation for
 
1379
     log10(x).  */
 
1380
  l *= 0.30102999566398119523;
 
1381
  /* Round down to the next integer.  */
 
1382
  return (int) l + (l < 0 ? -1 : 0);
 
1383
}
 
1384
 
 
1385
# endif
 
1386
 
 
1387
# if NEED_PRINTF_DOUBLE
 
1388
 
 
1389
/* Assuming x is finite and > 0:
 
1390
   Return an approximation for n with 10^n <= x < 10^(n+1).
 
1391
   The approximation is usually the right n, but may be off by 1 sometimes.  */
 
1392
static int
 
1393
floorlog10 (double x)
 
1394
{
 
1395
  int exp;
 
1396
  double y;
 
1397
  double z;
 
1398
  double l;
 
1399
 
 
1400
  /* Split into exponential part and mantissa.  */
 
1401
  y = frexp (x, &exp);
 
1402
  if (!(y >= 0.0 && y < 1.0))
 
1403
    abort ();
 
1404
  if (y == 0.0)
 
1405
    return INT_MIN;
 
1406
  if (y < 0.5)
 
1407
    {
 
1408
      while (y < (1.0 / (1 << (GMP_LIMB_BITS / 2)) / (1 << (GMP_LIMB_BITS / 2))))
 
1409
        {
 
1410
          y *= 1.0 * (1 << (GMP_LIMB_BITS / 2)) * (1 << (GMP_LIMB_BITS / 2));
 
1411
          exp -= GMP_LIMB_BITS;
 
1412
        }
 
1413
      if (y < (1.0 / (1 << 16)))
 
1414
        {
 
1415
          y *= 1.0 * (1 << 16);
 
1416
          exp -= 16;
 
1417
        }
 
1418
      if (y < (1.0 / (1 << 8)))
 
1419
        {
 
1420
          y *= 1.0 * (1 << 8);
 
1421
          exp -= 8;
 
1422
        }
 
1423
      if (y < (1.0 / (1 << 4)))
 
1424
        {
 
1425
          y *= 1.0 * (1 << 4);
 
1426
          exp -= 4;
 
1427
        }
 
1428
      if (y < (1.0 / (1 << 2)))
 
1429
        {
 
1430
          y *= 1.0 * (1 << 2);
 
1431
          exp -= 2;
 
1432
        }
 
1433
      if (y < (1.0 / (1 << 1)))
 
1434
        {
 
1435
          y *= 1.0 * (1 << 1);
 
1436
          exp -= 1;
 
1437
        }
 
1438
    }
 
1439
  if (!(y >= 0.5 && y < 1.0))
 
1440
    abort ();
 
1441
  /* Compute an approximation for l = log2(x) = exp + log2(y).  */
 
1442
  l = exp;
 
1443
  z = y;
 
1444
  if (z < 0.70710678118654752444)
 
1445
    {
 
1446
      z *= 1.4142135623730950488;
 
1447
      l -= 0.5;
 
1448
    }
 
1449
  if (z < 0.8408964152537145431)
 
1450
    {
 
1451
      z *= 1.1892071150027210667;
 
1452
      l -= 0.25;
 
1453
    }
 
1454
  if (z < 0.91700404320467123175)
 
1455
    {
 
1456
      z *= 1.0905077326652576592;
 
1457
      l -= 0.125;
 
1458
    }
 
1459
  if (z < 0.9576032806985736469)
 
1460
    {
 
1461
      z *= 1.0442737824274138403;
 
1462
      l -= 0.0625;
 
1463
    }
 
1464
  /* Now 0.95 <= z <= 1.01.  */
 
1465
  z = 1 - z;
 
1466
  /* log2(1-z) = 1/log(2) * (- z - z^2/2 - z^3/3 - z^4/4 - ...)
 
1467
     Four terms are enough to get an approximation with error < 10^-7.  */
 
1468
  l -= 1.4426950408889634074 * z * (1.0 + z * (0.5 + z * ((1.0 / 3) + z * 0.25)));
 
1469
  /* Finally multiply with log(2)/log(10), yields an approximation for
 
1470
     log10(x).  */
 
1471
  l *= 0.30102999566398119523;
 
1472
  /* Round down to the next integer.  */
 
1473
  return (int) l + (l < 0 ? -1 : 0);
 
1474
}
 
1475
 
 
1476
# endif
 
1477
 
 
1478
/* Tests whether a string of digits consists of exactly PRECISION zeroes and
 
1479
   a single '1' digit.  */
 
1480
static int
 
1481
is_borderline (const char *digits, size_t precision)
 
1482
{
 
1483
  for (; precision > 0; precision--, digits++)
 
1484
    if (*digits != '0')
 
1485
      return 0;
 
1486
  if (*digits != '1')
 
1487
    return 0;
 
1488
  digits++;
 
1489
  return *digits == '\0';
 
1490
}
 
1491
 
 
1492
#endif
 
1493
 
 
1494
#if !USE_SNPRINTF || !HAVE_SNPRINTF_RETVAL_C99
 
1495
 
 
1496
/* Use a different function name, to make it possible that the 'wchar_t'
 
1497
   parametrization and the 'char' parametrization get compiled in the same
 
1498
   translation unit.  */
 
1499
# if WIDE_CHAR_VERSION
 
1500
#  define MAX_ROOM_NEEDED wmax_room_needed
 
1501
# else
 
1502
#  define MAX_ROOM_NEEDED max_room_needed
 
1503
# endif
 
1504
 
 
1505
/* Returns the number of TCHAR_T units needed as temporary space for the result
 
1506
   of sprintf or SNPRINTF of a single conversion directive.  */
 
1507
static inline size_t
 
1508
MAX_ROOM_NEEDED (const arguments *ap, size_t arg_index, FCHAR_T conversion,
 
1509
                 arg_type type, int flags, size_t width, int has_precision,
 
1510
                 size_t precision, int pad_ourselves)
 
1511
{
 
1512
  size_t tmp_length;
 
1513
 
 
1514
  switch (conversion)
 
1515
    {
 
1516
    case 'd': case 'i': case 'u':
 
1517
# if HAVE_LONG_LONG_INT
 
1518
      if (type == TYPE_LONGLONGINT || type == TYPE_ULONGLONGINT)
 
1519
        tmp_length =
 
1520
          (unsigned int) (sizeof (unsigned long long) * CHAR_BIT
 
1521
                          * 0.30103 /* binary -> decimal */
 
1522
                         )
 
1523
          + 1; /* turn floor into ceil */
 
1524
      else
 
1525
# endif
 
1526
      if (type == TYPE_LONGINT || type == TYPE_ULONGINT)
 
1527
        tmp_length =
 
1528
          (unsigned int) (sizeof (unsigned long) * CHAR_BIT
 
1529
                          * 0.30103 /* binary -> decimal */
 
1530
                         )
 
1531
          + 1; /* turn floor into ceil */
 
1532
      else
 
1533
        tmp_length =
 
1534
          (unsigned int) (sizeof (unsigned int) * CHAR_BIT
 
1535
                          * 0.30103 /* binary -> decimal */
 
1536
                         )
 
1537
          + 1; /* turn floor into ceil */
 
1538
      if (tmp_length < precision)
 
1539
        tmp_length = precision;
 
1540
      /* Multiply by 2, as an estimate for FLAG_GROUP.  */
 
1541
      tmp_length = xsum (tmp_length, tmp_length);
 
1542
      /* Add 1, to account for a leading sign.  */
 
1543
      tmp_length = xsum (tmp_length, 1);
 
1544
      break;
 
1545
 
 
1546
    case 'o':
 
1547
# if HAVE_LONG_LONG_INT
 
1548
      if (type == TYPE_LONGLONGINT || type == TYPE_ULONGLONGINT)
 
1549
        tmp_length =
 
1550
          (unsigned int) (sizeof (unsigned long long) * CHAR_BIT
 
1551
                          * 0.333334 /* binary -> octal */
 
1552
                         )
 
1553
          + 1; /* turn floor into ceil */
 
1554
      else
 
1555
# endif
 
1556
      if (type == TYPE_LONGINT || type == TYPE_ULONGINT)
 
1557
        tmp_length =
 
1558
          (unsigned int) (sizeof (unsigned long) * CHAR_BIT
 
1559
                          * 0.333334 /* binary -> octal */
 
1560
                         )
 
1561
          + 1; /* turn floor into ceil */
 
1562
      else
 
1563
        tmp_length =
 
1564
          (unsigned int) (sizeof (unsigned int) * CHAR_BIT
 
1565
                          * 0.333334 /* binary -> octal */
 
1566
                         )
 
1567
          + 1; /* turn floor into ceil */
 
1568
      if (tmp_length < precision)
 
1569
        tmp_length = precision;
 
1570
      /* Add 1, to account for a leading sign.  */
 
1571
      tmp_length = xsum (tmp_length, 1);
 
1572
      break;
 
1573
 
 
1574
    case 'x': case 'X':
 
1575
# if HAVE_LONG_LONG_INT
 
1576
      if (type == TYPE_LONGLONGINT || type == TYPE_ULONGLONGINT)
 
1577
        tmp_length =
 
1578
          (unsigned int) (sizeof (unsigned long long) * CHAR_BIT
 
1579
                          * 0.25 /* binary -> hexadecimal */
 
1580
                         )
 
1581
          + 1; /* turn floor into ceil */
 
1582
      else
 
1583
# endif
 
1584
      if (type == TYPE_LONGINT || type == TYPE_ULONGINT)
 
1585
        tmp_length =
 
1586
          (unsigned int) (sizeof (unsigned long) * CHAR_BIT
 
1587
                          * 0.25 /* binary -> hexadecimal */
 
1588
                         )
 
1589
          + 1; /* turn floor into ceil */
 
1590
      else
 
1591
        tmp_length =
 
1592
          (unsigned int) (sizeof (unsigned int) * CHAR_BIT
 
1593
                          * 0.25 /* binary -> hexadecimal */
 
1594
                         )
 
1595
          + 1; /* turn floor into ceil */
 
1596
      if (tmp_length < precision)
 
1597
        tmp_length = precision;
 
1598
      /* Add 2, to account for a leading sign or alternate form.  */
 
1599
      tmp_length = xsum (tmp_length, 2);
 
1600
      break;
 
1601
 
 
1602
    case 'f': case 'F':
 
1603
      if (type == TYPE_LONGDOUBLE)
 
1604
        tmp_length =
 
1605
          (unsigned int) (LDBL_MAX_EXP
 
1606
                          * 0.30103 /* binary -> decimal */
 
1607
                          * 2 /* estimate for FLAG_GROUP */
 
1608
                         )
 
1609
          + 1 /* turn floor into ceil */
 
1610
          + 10; /* sign, decimal point etc. */
 
1611
      else
 
1612
        tmp_length =
 
1613
          (unsigned int) (DBL_MAX_EXP
 
1614
                          * 0.30103 /* binary -> decimal */
 
1615
                          * 2 /* estimate for FLAG_GROUP */
 
1616
                         )
 
1617
          + 1 /* turn floor into ceil */
 
1618
          + 10; /* sign, decimal point etc. */
 
1619
      tmp_length = xsum (tmp_length, precision);
 
1620
      break;
 
1621
 
 
1622
    case 'e': case 'E': case 'g': case 'G':
 
1623
      tmp_length =
 
1624
        12; /* sign, decimal point, exponent etc. */
 
1625
      tmp_length = xsum (tmp_length, precision);
 
1626
      break;
 
1627
 
 
1628
    case 'a': case 'A':
 
1629
      if (type == TYPE_LONGDOUBLE)
 
1630
        tmp_length =
 
1631
          (unsigned int) (LDBL_DIG
 
1632
                          * 0.831 /* decimal -> hexadecimal */
 
1633
                         )
 
1634
          + 1; /* turn floor into ceil */
 
1635
      else
 
1636
        tmp_length =
 
1637
          (unsigned int) (DBL_DIG
 
1638
                          * 0.831 /* decimal -> hexadecimal */
 
1639
                         )
 
1640
          + 1; /* turn floor into ceil */
 
1641
      if (tmp_length < precision)
 
1642
        tmp_length = precision;
 
1643
      /* Account for sign, decimal point etc. */
 
1644
      tmp_length = xsum (tmp_length, 12);
 
1645
      break;
 
1646
 
 
1647
    case 'c':
 
1648
# if HAVE_WINT_T && !WIDE_CHAR_VERSION
 
1649
      if (type == TYPE_WIDE_CHAR)
 
1650
        tmp_length = MB_CUR_MAX;
 
1651
      else
 
1652
# endif
 
1653
        tmp_length = 1;
 
1654
      break;
 
1655
 
 
1656
    case 's':
 
1657
# if HAVE_WCHAR_T
 
1658
      if (type == TYPE_WIDE_STRING)
 
1659
        {
 
1660
#  if WIDE_CHAR_VERSION
 
1661
          /* ISO C says about %ls in fwprintf:
 
1662
               "If the precision is not specified or is greater than the size
 
1663
                of the array, the array shall contain a null wide character."
 
1664
             So if there is a precision, we must not use wcslen.  */
 
1665
          const wchar_t *arg = ap->arg[arg_index].a.a_wide_string;
 
1666
 
 
1667
          if (has_precision)
 
1668
            tmp_length = local_wcsnlen (arg, precision);
 
1669
          else
 
1670
            tmp_length = local_wcslen (arg);
 
1671
#  else
 
1672
          /* ISO C says about %ls in fprintf:
 
1673
               "If a precision is specified, no more than that many bytes are
 
1674
                written (including shift sequences, if any), and the array
 
1675
                shall contain a null wide character if, to equal the multibyte
 
1676
                character sequence length given by the precision, the function
 
1677
                would need to access a wide character one past the end of the
 
1678
                array."
 
1679
             So if there is a precision, we must not use wcslen.  */
 
1680
          /* This case has already been handled separately in VASNPRINTF.  */
 
1681
          abort ();
 
1682
#  endif
 
1683
        }
 
1684
      else
 
1685
# endif
 
1686
        {
 
1687
# if WIDE_CHAR_VERSION
 
1688
          /* ISO C says about %s in fwprintf:
 
1689
               "If the precision is not specified or is greater than the size
 
1690
                of the converted array, the converted array shall contain a
 
1691
                null wide character."
 
1692
             So if there is a precision, we must not use strlen.  */
 
1693
          /* This case has already been handled separately in VASNPRINTF.  */
 
1694
          abort ();
 
1695
# else
 
1696
          /* ISO C says about %s in fprintf:
 
1697
               "If the precision is not specified or greater than the size of
 
1698
                the array, the array shall contain a null character."
 
1699
             So if there is a precision, we must not use strlen.  */
 
1700
          const char *arg = ap->arg[arg_index].a.a_string;
 
1701
 
 
1702
          if (has_precision)
 
1703
            tmp_length = local_strnlen (arg, precision);
 
1704
          else
 
1705
            tmp_length = strlen (arg);
 
1706
# endif
 
1707
        }
 
1708
      break;
 
1709
 
 
1710
    case 'p':
 
1711
      tmp_length =
 
1712
        (unsigned int) (sizeof (void *) * CHAR_BIT
 
1713
                        * 0.25 /* binary -> hexadecimal */
 
1714
                       )
 
1715
          + 1 /* turn floor into ceil */
 
1716
          + 2; /* account for leading 0x */
 
1717
      break;
 
1718
 
 
1719
    default:
 
1720
      abort ();
 
1721
    }
 
1722
 
 
1723
  if (!pad_ourselves)
 
1724
    {
 
1725
# if ENABLE_UNISTDIO
 
1726
      /* Padding considers the number of characters, therefore the number of
 
1727
         elements after padding may be
 
1728
           > max (tmp_length, width)
 
1729
         but is certainly
 
1730
           <= tmp_length + width.  */
 
1731
      tmp_length = xsum (tmp_length, width);
 
1732
# else
 
1733
      /* Padding considers the number of elements, says POSIX.  */
 
1734
      if (tmp_length < width)
 
1735
        tmp_length = width;
 
1736
# endif
 
1737
    }
 
1738
 
 
1739
  tmp_length = xsum (tmp_length, 1); /* account for trailing NUL */
 
1740
 
 
1741
  return tmp_length;
 
1742
}
 
1743
 
 
1744
#endif
 
1745
 
 
1746
DCHAR_T *
 
1747
VASNPRINTF (DCHAR_T *resultbuf, size_t *lengthp,
 
1748
            const FCHAR_T *format, va_list args)
 
1749
{
 
1750
  DIRECTIVES d;
 
1751
  arguments a;
 
1752
 
 
1753
  if (PRINTF_PARSE (format, &d, &a) < 0)
 
1754
    /* errno is already set.  */
 
1755
    return NULL;
 
1756
 
 
1757
#define CLEANUP() \
 
1758
  if (d.dir != d.direct_alloc_dir)                                      \
 
1759
    free (d.dir);                                                       \
 
1760
  if (a.arg != a.direct_alloc_arg)                                      \
 
1761
    free (a.arg);
 
1762
 
 
1763
  if (PRINTF_FETCHARGS (args, &a) < 0)
 
1764
    {
 
1765
      CLEANUP ();
 
1766
      errno = EINVAL;
 
1767
      return NULL;
 
1768
    }
 
1769
 
 
1770
  {
 
1771
    size_t buf_neededlength;
 
1772
    TCHAR_T *buf;
 
1773
    TCHAR_T *buf_malloced;
 
1774
    const FCHAR_T *cp;
 
1775
    size_t i;
 
1776
    DIRECTIVE *dp;
 
1777
    /* Output string accumulator.  */
 
1778
    DCHAR_T *result;
 
1779
    size_t allocated;
 
1780
    size_t length;
 
1781
 
 
1782
    /* Allocate a small buffer that will hold a directive passed to
 
1783
       sprintf or snprintf.  */
 
1784
    buf_neededlength =
 
1785
      xsum4 (7, d.max_width_length, d.max_precision_length, 6);
 
1786
#if HAVE_ALLOCA
 
1787
    if (buf_neededlength < 4000 / sizeof (TCHAR_T))
 
1788
      {
 
1789
        buf = (TCHAR_T *) alloca (buf_neededlength * sizeof (TCHAR_T));
 
1790
        buf_malloced = NULL;
 
1791
      }
 
1792
    else
 
1793
#endif
 
1794
      {
 
1795
        size_t buf_memsize = xtimes (buf_neededlength, sizeof (TCHAR_T));
 
1796
        if (size_overflow_p (buf_memsize))
 
1797
          goto out_of_memory_1;
 
1798
        buf = (TCHAR_T *) malloc (buf_memsize);
 
1799
        if (buf == NULL)
 
1800
          goto out_of_memory_1;
 
1801
        buf_malloced = buf;
 
1802
      }
 
1803
 
 
1804
    if (resultbuf != NULL)
 
1805
      {
 
1806
        result = resultbuf;
 
1807
        allocated = *lengthp;
 
1808
      }
 
1809
    else
 
1810
      {
 
1811
        result = NULL;
 
1812
        allocated = 0;
 
1813
      }
 
1814
    length = 0;
 
1815
    /* Invariants:
 
1816
       result is either == resultbuf or == NULL or malloc-allocated.
 
1817
       If length > 0, then result != NULL.  */
 
1818
 
 
1819
    /* Ensures that allocated >= needed.  Aborts through a jump to
 
1820
       out_of_memory if needed is SIZE_MAX or otherwise too big.  */
 
1821
#define ENSURE_ALLOCATION(needed) \
 
1822
    if ((needed) > allocated)                                                \
 
1823
      {                                                                      \
 
1824
        size_t memory_size;                                                  \
 
1825
        DCHAR_T *memory;                                                     \
 
1826
                                                                             \
 
1827
        allocated = (allocated > 0 ? xtimes (allocated, 2) : 12);            \
 
1828
        if ((needed) > allocated)                                            \
 
1829
          allocated = (needed);                                              \
 
1830
        memory_size = xtimes (allocated, sizeof (DCHAR_T));                  \
 
1831
        if (size_overflow_p (memory_size))                                   \
 
1832
          goto out_of_memory;                                                \
 
1833
        if (result == resultbuf || result == NULL)                           \
 
1834
          memory = (DCHAR_T *) malloc (memory_size);                         \
 
1835
        else                                                                 \
 
1836
          memory = (DCHAR_T *) realloc (result, memory_size);                \
 
1837
        if (memory == NULL)                                                  \
 
1838
          goto out_of_memory;                                                \
 
1839
        if (result == resultbuf && length > 0)                               \
 
1840
          DCHAR_CPY (memory, result, length);                                \
 
1841
        result = memory;                                                     \
 
1842
      }
 
1843
 
 
1844
    for (cp = format, i = 0, dp = &d.dir[0]; ; cp = dp->dir_end, i++, dp++)
 
1845
      {
 
1846
        if (cp != dp->dir_start)
 
1847
          {
 
1848
            size_t n = dp->dir_start - cp;
 
1849
            size_t augmented_length = xsum (length, n);
 
1850
 
 
1851
            ENSURE_ALLOCATION (augmented_length);
 
1852
            /* This copies a piece of FCHAR_T[] into a DCHAR_T[].  Here we
 
1853
               need that the format string contains only ASCII characters
 
1854
               if FCHAR_T and DCHAR_T are not the same type.  */
 
1855
            if (sizeof (FCHAR_T) == sizeof (DCHAR_T))
 
1856
              {
 
1857
                DCHAR_CPY (result + length, (const DCHAR_T *) cp, n);
 
1858
                length = augmented_length;
 
1859
              }
 
1860
            else
 
1861
              {
 
1862
                do
 
1863
                  result[length++] = (unsigned char) *cp++;
 
1864
                while (--n > 0);
 
1865
              }
 
1866
          }
 
1867
        if (i == d.count)
 
1868
          break;
 
1869
 
 
1870
        /* Execute a single directive.  */
 
1871
        if (dp->conversion == '%')
 
1872
          {
 
1873
            size_t augmented_length;
 
1874
 
 
1875
            if (!(dp->arg_index == ARG_NONE))
 
1876
              abort ();
 
1877
            augmented_length = xsum (length, 1);
 
1878
            ENSURE_ALLOCATION (augmented_length);
 
1879
            result[length] = '%';
 
1880
            length = augmented_length;
 
1881
          }
 
1882
        else
 
1883
          {
 
1884
            if (!(dp->arg_index != ARG_NONE))
 
1885
              abort ();
 
1886
 
 
1887
            if (dp->conversion == 'n')
 
1888
              {
 
1889
                switch (a.arg[dp->arg_index].type)
 
1890
                  {
 
1891
                  case TYPE_COUNT_SCHAR_POINTER:
 
1892
                    *a.arg[dp->arg_index].a.a_count_schar_pointer = length;
 
1893
                    break;
 
1894
                  case TYPE_COUNT_SHORT_POINTER:
 
1895
                    *a.arg[dp->arg_index].a.a_count_short_pointer = length;
 
1896
                    break;
 
1897
                  case TYPE_COUNT_INT_POINTER:
 
1898
                    *a.arg[dp->arg_index].a.a_count_int_pointer = length;
 
1899
                    break;
 
1900
                  case TYPE_COUNT_LONGINT_POINTER:
 
1901
                    *a.arg[dp->arg_index].a.a_count_longint_pointer = length;
 
1902
                    break;
 
1903
#if HAVE_LONG_LONG_INT
 
1904
                  case TYPE_COUNT_LONGLONGINT_POINTER:
 
1905
                    *a.arg[dp->arg_index].a.a_count_longlongint_pointer = length;
 
1906
                    break;
 
1907
#endif
 
1908
                  default:
 
1909
                    abort ();
 
1910
                  }
 
1911
              }
 
1912
#if ENABLE_UNISTDIO
 
1913
            /* The unistdio extensions.  */
 
1914
            else if (dp->conversion == 'U')
 
1915
              {
 
1916
                arg_type type = a.arg[dp->arg_index].type;
 
1917
                int flags = dp->flags;
 
1918
                int has_width;
 
1919
                size_t width;
 
1920
                int has_precision;
 
1921
                size_t precision;
 
1922
 
 
1923
                has_width = 0;
 
1924
                width = 0;
 
1925
                if (dp->width_start != dp->width_end)
 
1926
                  {
 
1927
                    if (dp->width_arg_index != ARG_NONE)
 
1928
                      {
 
1929
                        int arg;
 
1930
 
 
1931
                        if (!(a.arg[dp->width_arg_index].type == TYPE_INT))
 
1932
                          abort ();
 
1933
                        arg = a.arg[dp->width_arg_index].a.a_int;
 
1934
                        if (arg < 0)
 
1935
                          {
 
1936
                            /* "A negative field width is taken as a '-' flag
 
1937
                                followed by a positive field width."  */
 
1938
                            flags |= FLAG_LEFT;
 
1939
                            width = (unsigned int) (-arg);
 
1940
                          }
 
1941
                        else
 
1942
                          width = arg;
 
1943
                      }
 
1944
                    else
 
1945
                      {
 
1946
                        const FCHAR_T *digitp = dp->width_start;
 
1947
 
 
1948
                        do
 
1949
                          width = xsum (xtimes (width, 10), *digitp++ - '0');
 
1950
                        while (digitp != dp->width_end);
 
1951
                      }
 
1952
                    has_width = 1;
 
1953
                  }
 
1954
 
 
1955
                has_precision = 0;
 
1956
                precision = 0;
 
1957
                if (dp->precision_start != dp->precision_end)
 
1958
                  {
 
1959
                    if (dp->precision_arg_index != ARG_NONE)
 
1960
                      {
 
1961
                        int arg;
 
1962
 
 
1963
                        if (!(a.arg[dp->precision_arg_index].type == TYPE_INT))
 
1964
                          abort ();
 
1965
                        arg = a.arg[dp->precision_arg_index].a.a_int;
 
1966
                        /* "A negative precision is taken as if the precision
 
1967
                            were omitted."  */
 
1968
                        if (arg >= 0)
 
1969
                          {
 
1970
                            precision = arg;
 
1971
                            has_precision = 1;
 
1972
                          }
 
1973
                      }
 
1974
                    else
 
1975
                      {
 
1976
                        const FCHAR_T *digitp = dp->precision_start + 1;
 
1977
 
 
1978
                        precision = 0;
 
1979
                        while (digitp != dp->precision_end)
 
1980
                          precision = xsum (xtimes (precision, 10), *digitp++ - '0');
 
1981
                        has_precision = 1;
 
1982
                      }
 
1983
                  }
 
1984
 
 
1985
                switch (type)
 
1986
                  {
 
1987
                  case TYPE_U8_STRING:
 
1988
                    {
 
1989
                      const uint8_t *arg = a.arg[dp->arg_index].a.a_u8_string;
 
1990
                      const uint8_t *arg_end;
 
1991
                      size_t characters;
 
1992
 
 
1993
                      if (has_precision)
 
1994
                        {
 
1995
                          /* Use only PRECISION characters, from the left.  */
 
1996
                          arg_end = arg;
 
1997
                          characters = 0;
 
1998
                          for (; precision > 0; precision--)
 
1999
                            {
 
2000
                              int count = u8_strmblen (arg_end);
 
2001
                              if (count == 0)
 
2002
                                break;
 
2003
                              if (count < 0)
 
2004
                                {
 
2005
                                  if (!(result == resultbuf || result == NULL))
 
2006
                                    free (result);
 
2007
                                  if (buf_malloced != NULL)
 
2008
                                    free (buf_malloced);
 
2009
                                  CLEANUP ();
 
2010
                                  errno = EILSEQ;
 
2011
                                  return NULL;
 
2012
                                }
 
2013
                              arg_end += count;
 
2014
                              characters++;
 
2015
                            }
 
2016
                        }
 
2017
                      else if (has_width)
 
2018
                        {
 
2019
                          /* Use the entire string, and count the number of
 
2020
                             characters.  */
 
2021
                          arg_end = arg;
 
2022
                          characters = 0;
 
2023
                          for (;;)
 
2024
                            {
 
2025
                              int count = u8_strmblen (arg_end);
 
2026
                              if (count == 0)
 
2027
                                break;
 
2028
                              if (count < 0)
 
2029
                                {
 
2030
                                  if (!(result == resultbuf || result == NULL))
 
2031
                                    free (result);
 
2032
                                  if (buf_malloced != NULL)
 
2033
                                    free (buf_malloced);
 
2034
                                  CLEANUP ();
 
2035
                                  errno = EILSEQ;
 
2036
                                  return NULL;
 
2037
                                }
 
2038
                              arg_end += count;
 
2039
                              characters++;
 
2040
                            }
 
2041
                        }
 
2042
                      else
 
2043
                        {
 
2044
                          /* Use the entire string.  */
 
2045
                          arg_end = arg + u8_strlen (arg);
 
2046
                          /* The number of characters doesn't matter.  */
 
2047
                          characters = 0;
 
2048
                        }
 
2049
 
 
2050
                      if (has_width && width > characters
 
2051
                          && !(dp->flags & FLAG_LEFT))
 
2052
                        {
 
2053
                          size_t n = width - characters;
 
2054
                          ENSURE_ALLOCATION (xsum (length, n));
 
2055
                          DCHAR_SET (result + length, ' ', n);
 
2056
                          length += n;
 
2057
                        }
 
2058
 
 
2059
# if DCHAR_IS_UINT8_T
 
2060
                      {
 
2061
                        size_t n = arg_end - arg;
 
2062
                        ENSURE_ALLOCATION (xsum (length, n));
 
2063
                        DCHAR_CPY (result + length, arg, n);
 
2064
                        length += n;
 
2065
                      }
 
2066
# else
 
2067
                      { /* Convert.  */
 
2068
                        DCHAR_T *converted = result + length;
 
2069
                        size_t converted_len = allocated - length;
 
2070
#  if DCHAR_IS_TCHAR
 
2071
                        /* Convert from UTF-8 to locale encoding.  */
 
2072
                        converted =
 
2073
                          u8_conv_to_encoding (locale_charset (),
 
2074
                                               iconveh_question_mark,
 
2075
                                               arg, arg_end - arg, NULL,
 
2076
                                               converted, &converted_len);
 
2077
#  else
 
2078
                        /* Convert from UTF-8 to UTF-16/UTF-32.  */
 
2079
                        converted =
 
2080
                          U8_TO_DCHAR (arg, arg_end - arg,
 
2081
                                       converted, &converted_len);
 
2082
#  endif
 
2083
                        if (converted == NULL)
 
2084
                          {
 
2085
                            int saved_errno = errno;
 
2086
                            if (!(result == resultbuf || result == NULL))
 
2087
                              free (result);
 
2088
                            if (buf_malloced != NULL)
 
2089
                              free (buf_malloced);
 
2090
                            CLEANUP ();
 
2091
                            errno = saved_errno;
 
2092
                            return NULL;
 
2093
                          }
 
2094
                        if (converted != result + length)
 
2095
                          {
 
2096
                            ENSURE_ALLOCATION (xsum (length, converted_len));
 
2097
                            DCHAR_CPY (result + length, converted, converted_len);
 
2098
                            free (converted);
 
2099
                          }
 
2100
                        length += converted_len;
 
2101
                      }
 
2102
# endif
 
2103
 
 
2104
                      if (has_width && width > characters
 
2105
                          && (dp->flags & FLAG_LEFT))
 
2106
                        {
 
2107
                          size_t n = width - characters;
 
2108
                          ENSURE_ALLOCATION (xsum (length, n));
 
2109
                          DCHAR_SET (result + length, ' ', n);
 
2110
                          length += n;
 
2111
                        }
 
2112
                    }
 
2113
                    break;
 
2114
 
 
2115
                  case TYPE_U16_STRING:
 
2116
                    {
 
2117
                      const uint16_t *arg = a.arg[dp->arg_index].a.a_u16_string;
 
2118
                      const uint16_t *arg_end;
 
2119
                      size_t characters;
 
2120
 
 
2121
                      if (has_precision)
 
2122
                        {
 
2123
                          /* Use only PRECISION characters, from the left.  */
 
2124
                          arg_end = arg;
 
2125
                          characters = 0;
 
2126
                          for (; precision > 0; precision--)
 
2127
                            {
 
2128
                              int count = u16_strmblen (arg_end);
 
2129
                              if (count == 0)
 
2130
                                break;
 
2131
                              if (count < 0)
 
2132
                                {
 
2133
                                  if (!(result == resultbuf || result == NULL))
 
2134
                                    free (result);
 
2135
                                  if (buf_malloced != NULL)
 
2136
                                    free (buf_malloced);
 
2137
                                  CLEANUP ();
 
2138
                                  errno = EILSEQ;
 
2139
                                  return NULL;
 
2140
                                }
 
2141
                              arg_end += count;
 
2142
                              characters++;
 
2143
                            }
 
2144
                        }
 
2145
                      else if (has_width)
 
2146
                        {
 
2147
                          /* Use the entire string, and count the number of
 
2148
                             characters.  */
 
2149
                          arg_end = arg;
 
2150
                          characters = 0;
 
2151
                          for (;;)
 
2152
                            {
 
2153
                              int count = u16_strmblen (arg_end);
 
2154
                              if (count == 0)
 
2155
                                break;
 
2156
                              if (count < 0)
 
2157
                                {
 
2158
                                  if (!(result == resultbuf || result == NULL))
 
2159
                                    free (result);
 
2160
                                  if (buf_malloced != NULL)
 
2161
                                    free (buf_malloced);
 
2162
                                  CLEANUP ();
 
2163
                                  errno = EILSEQ;
 
2164
                                  return NULL;
 
2165
                                }
 
2166
                              arg_end += count;
 
2167
                              characters++;
 
2168
                            }
 
2169
                        }
 
2170
                      else
 
2171
                        {
 
2172
                          /* Use the entire string.  */
 
2173
                          arg_end = arg + u16_strlen (arg);
 
2174
                          /* The number of characters doesn't matter.  */
 
2175
                          characters = 0;
 
2176
                        }
 
2177
 
 
2178
                      if (has_width && width > characters
 
2179
                          && !(dp->flags & FLAG_LEFT))
 
2180
                        {
 
2181
                          size_t n = width - characters;
 
2182
                          ENSURE_ALLOCATION (xsum (length, n));
 
2183
                          DCHAR_SET (result + length, ' ', n);
 
2184
                          length += n;
 
2185
                        }
 
2186
 
 
2187
# if DCHAR_IS_UINT16_T
 
2188
                      {
 
2189
                        size_t n = arg_end - arg;
 
2190
                        ENSURE_ALLOCATION (xsum (length, n));
 
2191
                        DCHAR_CPY (result + length, arg, n);
 
2192
                        length += n;
 
2193
                      }
 
2194
# else
 
2195
                      { /* Convert.  */
 
2196
                        DCHAR_T *converted = result + length;
 
2197
                        size_t converted_len = allocated - length;
 
2198
#  if DCHAR_IS_TCHAR
 
2199
                        /* Convert from UTF-16 to locale encoding.  */
 
2200
                        converted =
 
2201
                          u16_conv_to_encoding (locale_charset (),
 
2202
                                                iconveh_question_mark,
 
2203
                                                arg, arg_end - arg, NULL,
 
2204
                                                converted, &converted_len);
 
2205
#  else
 
2206
                        /* Convert from UTF-16 to UTF-8/UTF-32.  */
 
2207
                        converted =
 
2208
                          U16_TO_DCHAR (arg, arg_end - arg,
 
2209
                                        converted, &converted_len);
 
2210
#  endif
 
2211
                        if (converted == NULL)
 
2212
                          {
 
2213
                            int saved_errno = errno;
 
2214
                            if (!(result == resultbuf || result == NULL))
 
2215
                              free (result);
 
2216
                            if (buf_malloced != NULL)
 
2217
                              free (buf_malloced);
 
2218
                            CLEANUP ();
 
2219
                            errno = saved_errno;
 
2220
                            return NULL;
 
2221
                          }
 
2222
                        if (converted != result + length)
 
2223
                          {
 
2224
                            ENSURE_ALLOCATION (xsum (length, converted_len));
 
2225
                            DCHAR_CPY (result + length, converted, converted_len);
 
2226
                            free (converted);
 
2227
                          }
 
2228
                        length += converted_len;
 
2229
                      }
 
2230
# endif
 
2231
 
 
2232
                      if (has_width && width > characters
 
2233
                          && (dp->flags & FLAG_LEFT))
 
2234
                        {
 
2235
                          size_t n = width - characters;
 
2236
                          ENSURE_ALLOCATION (xsum (length, n));
 
2237
                          DCHAR_SET (result + length, ' ', n);
 
2238
                          length += n;
 
2239
                        }
 
2240
                    }
 
2241
                    break;
 
2242
 
 
2243
                  case TYPE_U32_STRING:
 
2244
                    {
 
2245
                      const uint32_t *arg = a.arg[dp->arg_index].a.a_u32_string;
 
2246
                      const uint32_t *arg_end;
 
2247
                      size_t characters;
 
2248
 
 
2249
                      if (has_precision)
 
2250
                        {
 
2251
                          /* Use only PRECISION characters, from the left.  */
 
2252
                          arg_end = arg;
 
2253
                          characters = 0;
 
2254
                          for (; precision > 0; precision--)
 
2255
                            {
 
2256
                              int count = u32_strmblen (arg_end);
 
2257
                              if (count == 0)
 
2258
                                break;
 
2259
                              if (count < 0)
 
2260
                                {
 
2261
                                  if (!(result == resultbuf || result == NULL))
 
2262
                                    free (result);
 
2263
                                  if (buf_malloced != NULL)
 
2264
                                    free (buf_malloced);
 
2265
                                  CLEANUP ();
 
2266
                                  errno = EILSEQ;
 
2267
                                  return NULL;
 
2268
                                }
 
2269
                              arg_end += count;
 
2270
                              characters++;
 
2271
                            }
 
2272
                        }
 
2273
                      else if (has_width)
 
2274
                        {
 
2275
                          /* Use the entire string, and count the number of
 
2276
                             characters.  */
 
2277
                          arg_end = arg;
 
2278
                          characters = 0;
 
2279
                          for (;;)
 
2280
                            {
 
2281
                              int count = u32_strmblen (arg_end);
 
2282
                              if (count == 0)
 
2283
                                break;
 
2284
                              if (count < 0)
 
2285
                                {
 
2286
                                  if (!(result == resultbuf || result == NULL))
 
2287
                                    free (result);
 
2288
                                  if (buf_malloced != NULL)
 
2289
                                    free (buf_malloced);
 
2290
                                  CLEANUP ();
 
2291
                                  errno = EILSEQ;
 
2292
                                  return NULL;
 
2293
                                }
 
2294
                              arg_end += count;
 
2295
                              characters++;
 
2296
                            }
 
2297
                        }
 
2298
                      else
 
2299
                        {
 
2300
                          /* Use the entire string.  */
 
2301
                          arg_end = arg + u32_strlen (arg);
 
2302
                          /* The number of characters doesn't matter.  */
 
2303
                          characters = 0;
 
2304
                        }
 
2305
 
 
2306
                      if (has_width && width > characters
 
2307
                          && !(dp->flags & FLAG_LEFT))
 
2308
                        {
 
2309
                          size_t n = width - characters;
 
2310
                          ENSURE_ALLOCATION (xsum (length, n));
 
2311
                          DCHAR_SET (result + length, ' ', n);
 
2312
                          length += n;
 
2313
                        }
 
2314
 
 
2315
# if DCHAR_IS_UINT32_T
 
2316
                      {
 
2317
                        size_t n = arg_end - arg;
 
2318
                        ENSURE_ALLOCATION (xsum (length, n));
 
2319
                        DCHAR_CPY (result + length, arg, n);
 
2320
                        length += n;
 
2321
                      }
 
2322
# else
 
2323
                      { /* Convert.  */
 
2324
                        DCHAR_T *converted = result + length;
 
2325
                        size_t converted_len = allocated - length;
 
2326
#  if DCHAR_IS_TCHAR
 
2327
                        /* Convert from UTF-32 to locale encoding.  */
 
2328
                        converted =
 
2329
                          u32_conv_to_encoding (locale_charset (),
 
2330
                                                iconveh_question_mark,
 
2331
                                                arg, arg_end - arg, NULL,
 
2332
                                                converted, &converted_len);
 
2333
#  else
 
2334
                        /* Convert from UTF-32 to UTF-8/UTF-16.  */
 
2335
                        converted =
 
2336
                          U32_TO_DCHAR (arg, arg_end - arg,
 
2337
                                        converted, &converted_len);
 
2338
#  endif
 
2339
                        if (converted == NULL)
 
2340
                          {
 
2341
                            int saved_errno = errno;
 
2342
                            if (!(result == resultbuf || result == NULL))
 
2343
                              free (result);
 
2344
                            if (buf_malloced != NULL)
 
2345
                              free (buf_malloced);
 
2346
                            CLEANUP ();
 
2347
                            errno = saved_errno;
 
2348
                            return NULL;
 
2349
                          }
 
2350
                        if (converted != result + length)
 
2351
                          {
 
2352
                            ENSURE_ALLOCATION (xsum (length, converted_len));
 
2353
                            DCHAR_CPY (result + length, converted, converted_len);
 
2354
                            free (converted);
 
2355
                          }
 
2356
                        length += converted_len;
 
2357
                      }
 
2358
# endif
 
2359
 
 
2360
                      if (has_width && width > characters
 
2361
                          && (dp->flags & FLAG_LEFT))
 
2362
                        {
 
2363
                          size_t n = width - characters;
 
2364
                          ENSURE_ALLOCATION (xsum (length, n));
 
2365
                          DCHAR_SET (result + length, ' ', n);
 
2366
                          length += n;
 
2367
                        }
 
2368
                    }
 
2369
                    break;
 
2370
 
 
2371
                  default:
 
2372
                    abort ();
 
2373
                  }
 
2374
              }
 
2375
#endif
 
2376
#if (!USE_SNPRINTF || !HAVE_SNPRINTF_RETVAL_C99 || (NEED_PRINTF_DIRECTIVE_LS && !defined IN_LIBINTL)) && HAVE_WCHAR_T
 
2377
            else if (dp->conversion == 's'
 
2378
# if WIDE_CHAR_VERSION
 
2379
                     && a.arg[dp->arg_index].type != TYPE_WIDE_STRING
 
2380
# else
 
2381
                     && a.arg[dp->arg_index].type == TYPE_WIDE_STRING
 
2382
# endif
 
2383
                    )
 
2384
              {
 
2385
                /* The normal handling of the 's' directive below requires
 
2386
                   allocating a temporary buffer.  The determination of its
 
2387
                   length (tmp_length), in the case when a precision is
 
2388
                   specified, below requires a conversion between a char[]
 
2389
                   string and a wchar_t[] wide string.  It could be done, but
 
2390
                   we have no guarantee that the implementation of sprintf will
 
2391
                   use the exactly same algorithm.  Without this guarantee, it
 
2392
                   is possible to have buffer overrun bugs.  In order to avoid
 
2393
                   such bugs, we implement the entire processing of the 's'
 
2394
                   directive ourselves.  */
 
2395
                int flags = dp->flags;
 
2396
                int has_width;
 
2397
                size_t width;
 
2398
                int has_precision;
 
2399
                size_t precision;
 
2400
 
 
2401
                has_width = 0;
 
2402
                width = 0;
 
2403
                if (dp->width_start != dp->width_end)
 
2404
                  {
 
2405
                    if (dp->width_arg_index != ARG_NONE)
 
2406
                      {
 
2407
                        int arg;
 
2408
 
 
2409
                        if (!(a.arg[dp->width_arg_index].type == TYPE_INT))
 
2410
                          abort ();
 
2411
                        arg = a.arg[dp->width_arg_index].a.a_int;
 
2412
                        if (arg < 0)
 
2413
                          {
 
2414
                            /* "A negative field width is taken as a '-' flag
 
2415
                                followed by a positive field width."  */
 
2416
                            flags |= FLAG_LEFT;
 
2417
                            width = (unsigned int) (-arg);
 
2418
                          }
 
2419
                        else
 
2420
                          width = arg;
 
2421
                      }
 
2422
                    else
 
2423
                      {
 
2424
                        const FCHAR_T *digitp = dp->width_start;
 
2425
 
 
2426
                        do
 
2427
                          width = xsum (xtimes (width, 10), *digitp++ - '0');
 
2428
                        while (digitp != dp->width_end);
 
2429
                      }
 
2430
                    has_width = 1;
 
2431
                  }
 
2432
 
 
2433
                has_precision = 0;
 
2434
                precision = 6;
 
2435
                if (dp->precision_start != dp->precision_end)
 
2436
                  {
 
2437
                    if (dp->precision_arg_index != ARG_NONE)
 
2438
                      {
 
2439
                        int arg;
 
2440
 
 
2441
                        if (!(a.arg[dp->precision_arg_index].type == TYPE_INT))
 
2442
                          abort ();
 
2443
                        arg = a.arg[dp->precision_arg_index].a.a_int;
 
2444
                        /* "A negative precision is taken as if the precision
 
2445
                            were omitted."  */
 
2446
                        if (arg >= 0)
 
2447
                          {
 
2448
                            precision = arg;
 
2449
                            has_precision = 1;
 
2450
                          }
 
2451
                      }
 
2452
                    else
 
2453
                      {
 
2454
                        const FCHAR_T *digitp = dp->precision_start + 1;
 
2455
 
 
2456
                        precision = 0;
 
2457
                        while (digitp != dp->precision_end)
 
2458
                          precision = xsum (xtimes (precision, 10), *digitp++ - '0');
 
2459
                        has_precision = 1;
 
2460
                      }
 
2461
                  }
 
2462
 
 
2463
# if WIDE_CHAR_VERSION
 
2464
                /* %s in vasnwprintf.  See the specification of fwprintf.  */
 
2465
                {
 
2466
                  const char *arg = a.arg[dp->arg_index].a.a_string;
 
2467
                  const char *arg_end;
 
2468
                  size_t characters;
 
2469
 
 
2470
                  if (has_precision)
 
2471
                    {
 
2472
                      /* Use only as many bytes as needed to produce PRECISION
 
2473
                         wide characters, from the left.  */
 
2474
#  if HAVE_MBRTOWC
 
2475
                      mbstate_t state;
 
2476
                      memset (&state, '\0', sizeof (mbstate_t));
 
2477
#  endif
 
2478
                      arg_end = arg;
 
2479
                      characters = 0;
 
2480
                      for (; precision > 0; precision--)
 
2481
                        {
 
2482
                          int count;
 
2483
#  if HAVE_MBRTOWC
 
2484
                          count = mbrlen (arg_end, MB_CUR_MAX, &state);
 
2485
#  else
 
2486
                          count = mblen (arg_end, MB_CUR_MAX);
 
2487
#  endif
 
2488
                          if (count == 0)
 
2489
                            /* Found the terminating NUL.  */
 
2490
                            break;
 
2491
                          if (count < 0)
 
2492
                            {
 
2493
                              /* Invalid or incomplete multibyte character.  */
 
2494
                              if (!(result == resultbuf || result == NULL))
 
2495
                                free (result);
 
2496
                              if (buf_malloced != NULL)
 
2497
                                free (buf_malloced);
 
2498
                              CLEANUP ();
 
2499
                              errno = EILSEQ;
 
2500
                              return NULL;
 
2501
                            }
 
2502
                          arg_end += count;
 
2503
                          characters++;
 
2504
                        }
 
2505
                    }
 
2506
                  else if (has_width)
 
2507
                    {
 
2508
                      /* Use the entire string, and count the number of wide
 
2509
                         characters.  */
 
2510
#  if HAVE_MBRTOWC
 
2511
                      mbstate_t state;
 
2512
                      memset (&state, '\0', sizeof (mbstate_t));
 
2513
#  endif
 
2514
                      arg_end = arg;
 
2515
                      characters = 0;
 
2516
                      for (;;)
 
2517
                        {
 
2518
                          int count;
 
2519
#  if HAVE_MBRTOWC
 
2520
                          count = mbrlen (arg_end, MB_CUR_MAX, &state);
 
2521
#  else
 
2522
                          count = mblen (arg_end, MB_CUR_MAX);
 
2523
#  endif
 
2524
                          if (count == 0)
 
2525
                            /* Found the terminating NUL.  */
 
2526
                            break;
 
2527
                          if (count < 0)
 
2528
                            {
 
2529
                              /* Invalid or incomplete multibyte character.  */
 
2530
                              if (!(result == resultbuf || result == NULL))
 
2531
                                free (result);
 
2532
                              if (buf_malloced != NULL)
 
2533
                                free (buf_malloced);
 
2534
                              CLEANUP ();
 
2535
                              errno = EILSEQ;
 
2536
                              return NULL;
 
2537
                            }
 
2538
                          arg_end += count;
 
2539
                          characters++;
 
2540
                        }
 
2541
                    }
 
2542
                  else
 
2543
                    {
 
2544
                      /* Use the entire string.  */
 
2545
                      arg_end = arg + strlen (arg);
 
2546
                      /* The number of characters doesn't matter.  */
 
2547
                      characters = 0;
 
2548
                    }
 
2549
 
 
2550
                  if (has_width && width > characters
 
2551
                      && !(dp->flags & FLAG_LEFT))
 
2552
                    {
 
2553
                      size_t n = width - characters;
 
2554
                      ENSURE_ALLOCATION (xsum (length, n));
 
2555
                      DCHAR_SET (result + length, ' ', n);
 
2556
                      length += n;
 
2557
                    }
 
2558
 
 
2559
                  if (has_precision || has_width)
 
2560
                    {
 
2561
                      /* We know the number of wide characters in advance.  */
 
2562
                      size_t remaining;
 
2563
#  if HAVE_MBRTOWC
 
2564
                      mbstate_t state;
 
2565
                      memset (&state, '\0', sizeof (mbstate_t));
 
2566
#  endif
 
2567
                      ENSURE_ALLOCATION (xsum (length, characters));
 
2568
                      for (remaining = characters; remaining > 0; remaining--)
 
2569
                        {
 
2570
                          wchar_t wc;
 
2571
                          int count;
 
2572
#  if HAVE_MBRTOWC
 
2573
                          count = mbrtowc (&wc, arg, arg_end - arg, &state);
 
2574
#  else
 
2575
                          count = mbtowc (&wc, arg, arg_end - arg);
 
2576
#  endif
 
2577
                          if (count <= 0)
 
2578
                            /* mbrtowc not consistent with mbrlen, or mbtowc
 
2579
                               not consistent with mblen.  */
 
2580
                            abort ();
 
2581
                          result[length++] = wc;
 
2582
                          arg += count;
 
2583
                        }
 
2584
                      if (!(arg == arg_end))
 
2585
                        abort ();
 
2586
                    }
 
2587
                  else
 
2588
                    {
 
2589
#  if HAVE_MBRTOWC
 
2590
                      mbstate_t state;
 
2591
                      memset (&state, '\0', sizeof (mbstate_t));
 
2592
#  endif
 
2593
                      while (arg < arg_end)
 
2594
                        {
 
2595
                          wchar_t wc;
 
2596
                          int count;
 
2597
#  if HAVE_MBRTOWC
 
2598
                          count = mbrtowc (&wc, arg, arg_end - arg, &state);
 
2599
#  else
 
2600
                          count = mbtowc (&wc, arg, arg_end - arg);
 
2601
#  endif
 
2602
                          if (count <= 0)
 
2603
                            /* mbrtowc not consistent with mbrlen, or mbtowc
 
2604
                               not consistent with mblen.  */
 
2605
                            abort ();
 
2606
                          ENSURE_ALLOCATION (xsum (length, 1));
 
2607
                          result[length++] = wc;
 
2608
                          arg += count;
 
2609
                        }
 
2610
                    }
 
2611
 
 
2612
                  if (has_width && width > characters
 
2613
                      && (dp->flags & FLAG_LEFT))
 
2614
                    {
 
2615
                      size_t n = width - characters;
 
2616
                      ENSURE_ALLOCATION (xsum (length, n));
 
2617
                      DCHAR_SET (result + length, ' ', n);
 
2618
                      length += n;
 
2619
                    }
 
2620
                }
 
2621
# else
 
2622
                /* %ls in vasnprintf.  See the specification of fprintf.  */
 
2623
                {
 
2624
                  const wchar_t *arg = a.arg[dp->arg_index].a.a_wide_string;
 
2625
                  const wchar_t *arg_end;
 
2626
                  size_t characters;
 
2627
#  if !DCHAR_IS_TCHAR
 
2628
                  /* This code assumes that TCHAR_T is 'char'.  */
 
2629
                  verify (sizeof (TCHAR_T) == 1);
 
2630
                  TCHAR_T *tmpsrc;
 
2631
                  DCHAR_T *tmpdst;
 
2632
                  size_t tmpdst_len;
 
2633
#  endif
 
2634
                  size_t w;
 
2635
 
 
2636
                  if (has_precision)
 
2637
                    {
 
2638
                      /* Use only as many wide characters as needed to produce
 
2639
                         at most PRECISION bytes, from the left.  */
 
2640
#  if HAVE_WCRTOMB && !defined GNULIB_defined_mbstate_t
 
2641
                      mbstate_t state;
 
2642
                      memset (&state, '\0', sizeof (mbstate_t));
 
2643
#  endif
 
2644
                      arg_end = arg;
 
2645
                      characters = 0;
 
2646
                      while (precision > 0)
 
2647
                        {
 
2648
                          char cbuf[64]; /* Assume MB_CUR_MAX <= 64.  */
 
2649
                          int count;
 
2650
 
 
2651
                          if (*arg_end == 0)
 
2652
                            /* Found the terminating null wide character.  */
 
2653
                            break;
 
2654
#  if HAVE_WCRTOMB && !defined GNULIB_defined_mbstate_t
 
2655
                          count = wcrtomb (cbuf, *arg_end, &state);
 
2656
#  else
 
2657
                          count = wctomb (cbuf, *arg_end);
 
2658
#  endif
 
2659
                          if (count < 0)
 
2660
                            {
 
2661
                              /* Cannot convert.  */
 
2662
                              if (!(result == resultbuf || result == NULL))
 
2663
                                free (result);
 
2664
                              if (buf_malloced != NULL)
 
2665
                                free (buf_malloced);
 
2666
                              CLEANUP ();
 
2667
                              errno = EILSEQ;
 
2668
                              return NULL;
 
2669
                            }
 
2670
                          if (precision < count)
 
2671
                            break;
 
2672
                          arg_end++;
 
2673
                          characters += count;
 
2674
                          precision -= count;
 
2675
                        }
 
2676
                    }
 
2677
#  if DCHAR_IS_TCHAR
 
2678
                  else if (has_width)
 
2679
#  else
 
2680
                  else
 
2681
#  endif
 
2682
                    {
 
2683
                      /* Use the entire string, and count the number of
 
2684
                         bytes.  */
 
2685
#  if HAVE_WCRTOMB && !defined GNULIB_defined_mbstate_t
 
2686
                      mbstate_t state;
 
2687
                      memset (&state, '\0', sizeof (mbstate_t));
 
2688
#  endif
 
2689
                      arg_end = arg;
 
2690
                      characters = 0;
 
2691
                      for (;;)
 
2692
                        {
 
2693
                          char cbuf[64]; /* Assume MB_CUR_MAX <= 64.  */
 
2694
                          int count;
 
2695
 
 
2696
                          if (*arg_end == 0)
 
2697
                            /* Found the terminating null wide character.  */
 
2698
                            break;
 
2699
#  if HAVE_WCRTOMB && !defined GNULIB_defined_mbstate_t
 
2700
                          count = wcrtomb (cbuf, *arg_end, &state);
 
2701
#  else
 
2702
                          count = wctomb (cbuf, *arg_end);
 
2703
#  endif
 
2704
                          if (count < 0)
 
2705
                            {
 
2706
                              /* Cannot convert.  */
 
2707
                              if (!(result == resultbuf || result == NULL))
 
2708
                                free (result);
 
2709
                              if (buf_malloced != NULL)
 
2710
                                free (buf_malloced);
 
2711
                              CLEANUP ();
 
2712
                              errno = EILSEQ;
 
2713
                              return NULL;
 
2714
                            }
 
2715
                          arg_end++;
 
2716
                          characters += count;
 
2717
                        }
 
2718
                    }
 
2719
#  if DCHAR_IS_TCHAR
 
2720
                  else
 
2721
                    {
 
2722
                      /* Use the entire string.  */
 
2723
                      arg_end = arg + local_wcslen (arg);
 
2724
                      /* The number of bytes doesn't matter.  */
 
2725
                      characters = 0;
 
2726
                    }
 
2727
#  endif
 
2728
 
 
2729
#  if !DCHAR_IS_TCHAR
 
2730
                  /* Convert the string into a piece of temporary memory.  */
 
2731
                  tmpsrc = (TCHAR_T *) malloc (characters * sizeof (TCHAR_T));
 
2732
                  if (tmpsrc == NULL)
 
2733
                    goto out_of_memory;
 
2734
                  {
 
2735
                    TCHAR_T *tmpptr = tmpsrc;
 
2736
                    size_t remaining;
 
2737
#   if HAVE_WCRTOMB && !defined GNULIB_defined_mbstate_t
 
2738
                    mbstate_t state;
 
2739
                    memset (&state, '\0', sizeof (mbstate_t));
 
2740
#   endif
 
2741
                    for (remaining = characters; remaining > 0; )
 
2742
                      {
 
2743
                        char cbuf[64]; /* Assume MB_CUR_MAX <= 64.  */
 
2744
                        int count;
 
2745
 
 
2746
                        if (*arg == 0)
 
2747
                          abort ();
 
2748
#   if HAVE_WCRTOMB && !defined GNULIB_defined_mbstate_t
 
2749
                        count = wcrtomb (cbuf, *arg, &state);
 
2750
#   else
 
2751
                        count = wctomb (cbuf, *arg);
 
2752
#   endif
 
2753
                        if (count <= 0)
 
2754
                          /* Inconsistency.  */
 
2755
                          abort ();
 
2756
                        memcpy (tmpptr, cbuf, count);
 
2757
                        tmpptr += count;
 
2758
                        arg++;
 
2759
                        remaining -= count;
 
2760
                      }
 
2761
                    if (!(arg == arg_end))
 
2762
                      abort ();
 
2763
                  }
 
2764
 
 
2765
                  /* Convert from TCHAR_T[] to DCHAR_T[].  */
 
2766
                  tmpdst =
 
2767
                    DCHAR_CONV_FROM_ENCODING (locale_charset (),
 
2768
                                              iconveh_question_mark,
 
2769
                                              tmpsrc, characters,
 
2770
                                              NULL,
 
2771
                                              NULL, &tmpdst_len);
 
2772
                  if (tmpdst == NULL)
 
2773
                    {
 
2774
                      int saved_errno = errno;
 
2775
                      free (tmpsrc);
 
2776
                      if (!(result == resultbuf || result == NULL))
 
2777
                        free (result);
 
2778
                      if (buf_malloced != NULL)
 
2779
                        free (buf_malloced);
 
2780
                      CLEANUP ();
 
2781
                      errno = saved_errno;
 
2782
                      return NULL;
 
2783
                    }
 
2784
                  free (tmpsrc);
 
2785
#  endif
 
2786
 
 
2787
                  if (has_width)
 
2788
                    {
 
2789
#  if ENABLE_UNISTDIO
 
2790
                      /* Outside POSIX, it's preferrable to compare the width
 
2791
                         against the number of _characters_ of the converted
 
2792
                         value.  */
 
2793
                      w = DCHAR_MBSNLEN (result + length, characters);
 
2794
#  else
 
2795
                      /* The width is compared against the number of _bytes_
 
2796
                         of the converted value, says POSIX.  */
 
2797
                      w = characters;
 
2798
#  endif
 
2799
                    }
 
2800
                  else
 
2801
                    /* w doesn't matter.  */
 
2802
                    w = 0;
 
2803
 
 
2804
                  if (has_width && width > w
 
2805
                      && !(dp->flags & FLAG_LEFT))
 
2806
                    {
 
2807
                      size_t n = width - w;
 
2808
                      ENSURE_ALLOCATION (xsum (length, n));
 
2809
                      DCHAR_SET (result + length, ' ', n);
 
2810
                      length += n;
 
2811
                    }
 
2812
 
 
2813
#  if DCHAR_IS_TCHAR
 
2814
                  if (has_precision || has_width)
 
2815
                    {
 
2816
                      /* We know the number of bytes in advance.  */
 
2817
                      size_t remaining;
 
2818
#   if HAVE_WCRTOMB && !defined GNULIB_defined_mbstate_t
 
2819
                      mbstate_t state;
 
2820
                      memset (&state, '\0', sizeof (mbstate_t));
 
2821
#   endif
 
2822
                      ENSURE_ALLOCATION (xsum (length, characters));
 
2823
                      for (remaining = characters; remaining > 0; )
 
2824
                        {
 
2825
                          char cbuf[64]; /* Assume MB_CUR_MAX <= 64.  */
 
2826
                          int count;
 
2827
 
 
2828
                          if (*arg == 0)
 
2829
                            abort ();
 
2830
#   if HAVE_WCRTOMB && !defined GNULIB_defined_mbstate_t
 
2831
                          count = wcrtomb (cbuf, *arg, &state);
 
2832
#   else
 
2833
                          count = wctomb (cbuf, *arg);
 
2834
#   endif
 
2835
                          if (count <= 0)
 
2836
                            /* Inconsistency.  */
 
2837
                            abort ();
 
2838
                          memcpy (result + length, cbuf, count);
 
2839
                          length += count;
 
2840
                          arg++;
 
2841
                          remaining -= count;
 
2842
                        }
 
2843
                      if (!(arg == arg_end))
 
2844
                        abort ();
 
2845
                    }
 
2846
                  else
 
2847
                    {
 
2848
#   if HAVE_WCRTOMB && !defined GNULIB_defined_mbstate_t
 
2849
                      mbstate_t state;
 
2850
                      memset (&state, '\0', sizeof (mbstate_t));
 
2851
#   endif
 
2852
                      while (arg < arg_end)
 
2853
                        {
 
2854
                          char cbuf[64]; /* Assume MB_CUR_MAX <= 64.  */
 
2855
                          int count;
 
2856
 
 
2857
                          if (*arg == 0)
 
2858
                            abort ();
 
2859
#   if HAVE_WCRTOMB && !defined GNULIB_defined_mbstate_t
 
2860
                          count = wcrtomb (cbuf, *arg, &state);
 
2861
#   else
 
2862
                          count = wctomb (cbuf, *arg);
 
2863
#   endif
 
2864
                          if (count <= 0)
 
2865
                            {
 
2866
                              /* Cannot convert.  */
 
2867
                              if (!(result == resultbuf || result == NULL))
 
2868
                                free (result);
 
2869
                              if (buf_malloced != NULL)
 
2870
                                free (buf_malloced);
 
2871
                              CLEANUP ();
 
2872
                              errno = EILSEQ;
 
2873
                              return NULL;
 
2874
                            }
 
2875
                          ENSURE_ALLOCATION (xsum (length, count));
 
2876
                          memcpy (result + length, cbuf, count);
 
2877
                          length += count;
 
2878
                          arg++;
 
2879
                        }
 
2880
                    }
 
2881
#  else
 
2882
                  ENSURE_ALLOCATION (xsum (length, tmpdst_len));
 
2883
                  DCHAR_CPY (result + length, tmpdst, tmpdst_len);
 
2884
                  free (tmpdst);
 
2885
                  length += tmpdst_len;
 
2886
#  endif
 
2887
 
 
2888
                  if (has_width && width > w
 
2889
                      && (dp->flags & FLAG_LEFT))
 
2890
                    {
 
2891
                      size_t n = width - w;
 
2892
                      ENSURE_ALLOCATION (xsum (length, n));
 
2893
                      DCHAR_SET (result + length, ' ', n);
 
2894
                      length += n;
 
2895
                    }
 
2896
                }
 
2897
# endif
 
2898
              }
 
2899
#endif
 
2900
#if (NEED_PRINTF_DIRECTIVE_A || NEED_PRINTF_LONG_DOUBLE || NEED_PRINTF_DOUBLE) && !defined IN_LIBINTL
 
2901
            else if ((dp->conversion == 'a' || dp->conversion == 'A')
 
2902
# if !(NEED_PRINTF_DIRECTIVE_A || (NEED_PRINTF_LONG_DOUBLE && NEED_PRINTF_DOUBLE))
 
2903
                     && (0
 
2904
#  if NEED_PRINTF_DOUBLE
 
2905
                         || a.arg[dp->arg_index].type == TYPE_DOUBLE
 
2906
#  endif
 
2907
#  if NEED_PRINTF_LONG_DOUBLE
 
2908
                         || a.arg[dp->arg_index].type == TYPE_LONGDOUBLE
 
2909
#  endif
 
2910
                        )
 
2911
# endif
 
2912
                    )
 
2913
              {
 
2914
                arg_type type = a.arg[dp->arg_index].type;
 
2915
                int flags = dp->flags;
 
2916
                int has_width;
 
2917
                size_t width;
 
2918
                int has_precision;
 
2919
                size_t precision;
 
2920
                size_t tmp_length;
 
2921
                DCHAR_T tmpbuf[700];
 
2922
                DCHAR_T *tmp;
 
2923
                DCHAR_T *pad_ptr;
 
2924
                DCHAR_T *p;
 
2925
 
 
2926
                has_width = 0;
 
2927
                width = 0;
 
2928
                if (dp->width_start != dp->width_end)
 
2929
                  {
 
2930
                    if (dp->width_arg_index != ARG_NONE)
 
2931
                      {
 
2932
                        int arg;
 
2933
 
 
2934
                        if (!(a.arg[dp->width_arg_index].type == TYPE_INT))
 
2935
                          abort ();
 
2936
                        arg = a.arg[dp->width_arg_index].a.a_int;
 
2937
                        if (arg < 0)
 
2938
                          {
 
2939
                            /* "A negative field width is taken as a '-' flag
 
2940
                                followed by a positive field width."  */
 
2941
                            flags |= FLAG_LEFT;
 
2942
                            width = (unsigned int) (-arg);
 
2943
                          }
 
2944
                        else
 
2945
                          width = arg;
 
2946
                      }
 
2947
                    else
 
2948
                      {
 
2949
                        const FCHAR_T *digitp = dp->width_start;
 
2950
 
 
2951
                        do
 
2952
                          width = xsum (xtimes (width, 10), *digitp++ - '0');
 
2953
                        while (digitp != dp->width_end);
 
2954
                      }
 
2955
                    has_width = 1;
 
2956
                  }
 
2957
 
 
2958
                has_precision = 0;
 
2959
                precision = 0;
 
2960
                if (dp->precision_start != dp->precision_end)
 
2961
                  {
 
2962
                    if (dp->precision_arg_index != ARG_NONE)
 
2963
                      {
 
2964
                        int arg;
 
2965
 
 
2966
                        if (!(a.arg[dp->precision_arg_index].type == TYPE_INT))
 
2967
                          abort ();
 
2968
                        arg = a.arg[dp->precision_arg_index].a.a_int;
 
2969
                        /* "A negative precision is taken as if the precision
 
2970
                            were omitted."  */
 
2971
                        if (arg >= 0)
 
2972
                          {
 
2973
                            precision = arg;
 
2974
                            has_precision = 1;
 
2975
                          }
 
2976
                      }
 
2977
                    else
 
2978
                      {
 
2979
                        const FCHAR_T *digitp = dp->precision_start + 1;
 
2980
 
 
2981
                        precision = 0;
 
2982
                        while (digitp != dp->precision_end)
 
2983
                          precision = xsum (xtimes (precision, 10), *digitp++ - '0');
 
2984
                        has_precision = 1;
 
2985
                      }
 
2986
                  }
 
2987
 
 
2988
                /* Allocate a temporary buffer of sufficient size.  */
 
2989
                if (type == TYPE_LONGDOUBLE)
 
2990
                  tmp_length =
 
2991
                    (unsigned int) ((LDBL_DIG + 1)
 
2992
                                    * 0.831 /* decimal -> hexadecimal */
 
2993
                                   )
 
2994
                    + 1; /* turn floor into ceil */
 
2995
                else
 
2996
                  tmp_length =
 
2997
                    (unsigned int) ((DBL_DIG + 1)
 
2998
                                    * 0.831 /* decimal -> hexadecimal */
 
2999
                                   )
 
3000
                    + 1; /* turn floor into ceil */
 
3001
                if (tmp_length < precision)
 
3002
                  tmp_length = precision;
 
3003
                /* Account for sign, decimal point etc. */
 
3004
                tmp_length = xsum (tmp_length, 12);
 
3005
 
 
3006
                if (tmp_length < width)
 
3007
                  tmp_length = width;
 
3008
 
 
3009
                tmp_length = xsum (tmp_length, 1); /* account for trailing NUL */
 
3010
 
 
3011
                if (tmp_length <= sizeof (tmpbuf) / sizeof (DCHAR_T))
 
3012
                  tmp = tmpbuf;
 
3013
                else
 
3014
                  {
 
3015
                    size_t tmp_memsize = xtimes (tmp_length, sizeof (DCHAR_T));
 
3016
 
 
3017
                    if (size_overflow_p (tmp_memsize))
 
3018
                      /* Overflow, would lead to out of memory.  */
 
3019
                      goto out_of_memory;
 
3020
                    tmp = (DCHAR_T *) malloc (tmp_memsize);
 
3021
                    if (tmp == NULL)
 
3022
                      /* Out of memory.  */
 
3023
                      goto out_of_memory;
 
3024
                  }
 
3025
 
 
3026
                pad_ptr = NULL;
 
3027
                p = tmp;
 
3028
                if (type == TYPE_LONGDOUBLE)
 
3029
                  {
 
3030
# if NEED_PRINTF_DIRECTIVE_A || NEED_PRINTF_LONG_DOUBLE
 
3031
                    long double arg = a.arg[dp->arg_index].a.a_longdouble;
 
3032
 
 
3033
                    if (isnanl (arg))
 
3034
                      {
 
3035
                        if (dp->conversion == 'A')
 
3036
                          {
 
3037
                            *p++ = 'N'; *p++ = 'A'; *p++ = 'N';
 
3038
                          }
 
3039
                        else
 
3040
                          {
 
3041
                            *p++ = 'n'; *p++ = 'a'; *p++ = 'n';
 
3042
                          }
 
3043
                      }
 
3044
                    else
 
3045
                      {
 
3046
                        int sign = 0;
 
3047
                        DECL_LONG_DOUBLE_ROUNDING
 
3048
 
 
3049
                        BEGIN_LONG_DOUBLE_ROUNDING ();
 
3050
 
 
3051
                        if (signbit (arg)) /* arg < 0.0L or negative zero */
 
3052
                          {
 
3053
                            sign = -1;
 
3054
                            arg = -arg;
 
3055
                          }
 
3056
 
 
3057
                        if (sign < 0)
 
3058
                          *p++ = '-';
 
3059
                        else if (flags & FLAG_SHOWSIGN)
 
3060
                          *p++ = '+';
 
3061
                        else if (flags & FLAG_SPACE)
 
3062
                          *p++ = ' ';
 
3063
 
 
3064
                        if (arg > 0.0L && arg + arg == arg)
 
3065
                          {
 
3066
                            if (dp->conversion == 'A')
 
3067
                              {
 
3068
                                *p++ = 'I'; *p++ = 'N'; *p++ = 'F';
 
3069
                              }
 
3070
                            else
 
3071
                              {
 
3072
                                *p++ = 'i'; *p++ = 'n'; *p++ = 'f';
 
3073
                              }
 
3074
                          }
 
3075
                        else
 
3076
                          {
 
3077
                            int exponent;
 
3078
                            long double mantissa;
 
3079
 
 
3080
                            if (arg > 0.0L)
 
3081
                              mantissa = printf_frexpl (arg, &exponent);
 
3082
                            else
 
3083
                              {
 
3084
                                exponent = 0;
 
3085
                                mantissa = 0.0L;
 
3086
                              }
 
3087
 
 
3088
                            if (has_precision
 
3089
                                && precision < (unsigned int) ((LDBL_DIG + 1) * 0.831) + 1)
 
3090
                              {
 
3091
                                /* Round the mantissa.  */
 
3092
                                long double tail = mantissa;
 
3093
                                size_t q;
 
3094
 
 
3095
                                for (q = precision; ; q--)
 
3096
                                  {
 
3097
                                    int digit = (int) tail;
 
3098
                                    tail -= digit;
 
3099
                                    if (q == 0)
 
3100
                                      {
 
3101
                                        if (digit & 1 ? tail >= 0.5L : tail > 0.5L)
 
3102
                                          tail = 1 - tail;
 
3103
                                        else
 
3104
                                          tail = - tail;
 
3105
                                        break;
 
3106
                                      }
 
3107
                                    tail *= 16.0L;
 
3108
                                  }
 
3109
                                if (tail != 0.0L)
 
3110
                                  for (q = precision; q > 0; q--)
 
3111
                                    tail *= 0.0625L;
 
3112
                                mantissa += tail;
 
3113
                              }
 
3114
 
 
3115
                            *p++ = '0';
 
3116
                            *p++ = dp->conversion - 'A' + 'X';
 
3117
                            pad_ptr = p;
 
3118
                            {
 
3119
                              int digit;
 
3120
 
 
3121
                              digit = (int) mantissa;
 
3122
                              mantissa -= digit;
 
3123
                              *p++ = '0' + digit;
 
3124
                              if ((flags & FLAG_ALT)
 
3125
                                  || mantissa > 0.0L || precision > 0)
 
3126
                                {
 
3127
                                  *p++ = decimal_point_char ();
 
3128
                                  /* This loop terminates because we assume
 
3129
                                     that FLT_RADIX is a power of 2.  */
 
3130
                                  while (mantissa > 0.0L)
 
3131
                                    {
 
3132
                                      mantissa *= 16.0L;
 
3133
                                      digit = (int) mantissa;
 
3134
                                      mantissa -= digit;
 
3135
                                      *p++ = digit
 
3136
                                             + (digit < 10
 
3137
                                                ? '0'
 
3138
                                                : dp->conversion - 10);
 
3139
                                      if (precision > 0)
 
3140
                                        precision--;
 
3141
                                    }
 
3142
                                  while (precision > 0)
 
3143
                                    {
 
3144
                                      *p++ = '0';
 
3145
                                      precision--;
 
3146
                                    }
 
3147
                                }
 
3148
                              }
 
3149
                              *p++ = dp->conversion - 'A' + 'P';
 
3150
#  if WIDE_CHAR_VERSION
 
3151
                              {
 
3152
                                static const wchar_t decimal_format[] =
 
3153
                                  { '%', '+', 'd', '\0' };
 
3154
                                SNPRINTF (p, 6 + 1, decimal_format, exponent);
 
3155
                              }
 
3156
                              while (*p != '\0')
 
3157
                                p++;
 
3158
#  else
 
3159
                              if (sizeof (DCHAR_T) == 1)
 
3160
                                {
 
3161
                                  sprintf ((char *) p, "%+d", exponent);
 
3162
                                  while (*p != '\0')
 
3163
                                    p++;
 
3164
                                }
 
3165
                              else
 
3166
                                {
 
3167
                                  char expbuf[6 + 1];
 
3168
                                  const char *ep;
 
3169
                                  sprintf (expbuf, "%+d", exponent);
 
3170
                                  for (ep = expbuf; (*p = *ep) != '\0'; ep++)
 
3171
                                    p++;
 
3172
                                }
 
3173
#  endif
 
3174
                          }
 
3175
 
 
3176
                        END_LONG_DOUBLE_ROUNDING ();
 
3177
                      }
 
3178
# else
 
3179
                    abort ();
 
3180
# endif
 
3181
                  }
 
3182
                else
 
3183
                  {
 
3184
# if NEED_PRINTF_DIRECTIVE_A || NEED_PRINTF_DOUBLE
 
3185
                    double arg = a.arg[dp->arg_index].a.a_double;
 
3186
 
 
3187
                    if (isnand (arg))
 
3188
                      {
 
3189
                        if (dp->conversion == 'A')
 
3190
                          {
 
3191
                            *p++ = 'N'; *p++ = 'A'; *p++ = 'N';
 
3192
                          }
 
3193
                        else
 
3194
                          {
 
3195
                            *p++ = 'n'; *p++ = 'a'; *p++ = 'n';
 
3196
                          }
 
3197
                      }
 
3198
                    else
 
3199
                      {
 
3200
                        int sign = 0;
 
3201
 
 
3202
                        if (signbit (arg)) /* arg < 0.0 or negative zero */
 
3203
                          {
 
3204
                            sign = -1;
 
3205
                            arg = -arg;
 
3206
                          }
 
3207
 
 
3208
                        if (sign < 0)
 
3209
                          *p++ = '-';
 
3210
                        else if (flags & FLAG_SHOWSIGN)
 
3211
                          *p++ = '+';
 
3212
                        else if (flags & FLAG_SPACE)
 
3213
                          *p++ = ' ';
 
3214
 
 
3215
                        if (arg > 0.0 && arg + arg == arg)
 
3216
                          {
 
3217
                            if (dp->conversion == 'A')
 
3218
                              {
 
3219
                                *p++ = 'I'; *p++ = 'N'; *p++ = 'F';
 
3220
                              }
 
3221
                            else
 
3222
                              {
 
3223
                                *p++ = 'i'; *p++ = 'n'; *p++ = 'f';
 
3224
                              }
 
3225
                          }
 
3226
                        else
 
3227
                          {
 
3228
                            int exponent;
 
3229
                            double mantissa;
 
3230
 
 
3231
                            if (arg > 0.0)
 
3232
                              mantissa = printf_frexp (arg, &exponent);
 
3233
                            else
 
3234
                              {
 
3235
                                exponent = 0;
 
3236
                                mantissa = 0.0;
 
3237
                              }
 
3238
 
 
3239
                            if (has_precision
 
3240
                                && precision < (unsigned int) ((DBL_DIG + 1) * 0.831) + 1)
 
3241
                              {
 
3242
                                /* Round the mantissa.  */
 
3243
                                double tail = mantissa;
 
3244
                                size_t q;
 
3245
 
 
3246
                                for (q = precision; ; q--)
 
3247
                                  {
 
3248
                                    int digit = (int) tail;
 
3249
                                    tail -= digit;
 
3250
                                    if (q == 0)
 
3251
                                      {
 
3252
                                        if (digit & 1 ? tail >= 0.5 : tail > 0.5)
 
3253
                                          tail = 1 - tail;
 
3254
                                        else
 
3255
                                          tail = - tail;
 
3256
                                        break;
 
3257
                                      }
 
3258
                                    tail *= 16.0;
 
3259
                                  }
 
3260
                                if (tail != 0.0)
 
3261
                                  for (q = precision; q > 0; q--)
 
3262
                                    tail *= 0.0625;
 
3263
                                mantissa += tail;
 
3264
                              }
 
3265
 
 
3266
                            *p++ = '0';
 
3267
                            *p++ = dp->conversion - 'A' + 'X';
 
3268
                            pad_ptr = p;
 
3269
                            {
 
3270
                              int digit;
 
3271
 
 
3272
                              digit = (int) mantissa;
 
3273
                              mantissa -= digit;
 
3274
                              *p++ = '0' + digit;
 
3275
                              if ((flags & FLAG_ALT)
 
3276
                                  || mantissa > 0.0 || precision > 0)
 
3277
                                {
 
3278
                                  *p++ = decimal_point_char ();
 
3279
                                  /* This loop terminates because we assume
 
3280
                                     that FLT_RADIX is a power of 2.  */
 
3281
                                  while (mantissa > 0.0)
 
3282
                                    {
 
3283
                                      mantissa *= 16.0;
 
3284
                                      digit = (int) mantissa;
 
3285
                                      mantissa -= digit;
 
3286
                                      *p++ = digit
 
3287
                                             + (digit < 10
 
3288
                                                ? '0'
 
3289
                                                : dp->conversion - 10);
 
3290
                                      if (precision > 0)
 
3291
                                        precision--;
 
3292
                                    }
 
3293
                                  while (precision > 0)
 
3294
                                    {
 
3295
                                      *p++ = '0';
 
3296
                                      precision--;
 
3297
                                    }
 
3298
                                }
 
3299
                              }
 
3300
                              *p++ = dp->conversion - 'A' + 'P';
 
3301
#  if WIDE_CHAR_VERSION
 
3302
                              {
 
3303
                                static const wchar_t decimal_format[] =
 
3304
                                  { '%', '+', 'd', '\0' };
 
3305
                                SNPRINTF (p, 6 + 1, decimal_format, exponent);
 
3306
                              }
 
3307
                              while (*p != '\0')
 
3308
                                p++;
 
3309
#  else
 
3310
                              if (sizeof (DCHAR_T) == 1)
 
3311
                                {
 
3312
                                  sprintf ((char *) p, "%+d", exponent);
 
3313
                                  while (*p != '\0')
 
3314
                                    p++;
 
3315
                                }
 
3316
                              else
 
3317
                                {
 
3318
                                  char expbuf[6 + 1];
 
3319
                                  const char *ep;
 
3320
                                  sprintf (expbuf, "%+d", exponent);
 
3321
                                  for (ep = expbuf; (*p = *ep) != '\0'; ep++)
 
3322
                                    p++;
 
3323
                                }
 
3324
#  endif
 
3325
                          }
 
3326
                      }
 
3327
# else
 
3328
                    abort ();
 
3329
# endif
 
3330
                  }
 
3331
                /* The generated string now extends from tmp to p, with the
 
3332
                   zero padding insertion point being at pad_ptr.  */
 
3333
                if (has_width && p - tmp < width)
 
3334
                  {
 
3335
                    size_t pad = width - (p - tmp);
 
3336
                    DCHAR_T *end = p + pad;
 
3337
 
 
3338
                    if (flags & FLAG_LEFT)
 
3339
                      {
 
3340
                        /* Pad with spaces on the right.  */
 
3341
                        for (; pad > 0; pad--)
 
3342
                          *p++ = ' ';
 
3343
                      }
 
3344
                    else if ((flags & FLAG_ZERO) && pad_ptr != NULL)
 
3345
                      {
 
3346
                        /* Pad with zeroes.  */
 
3347
                        DCHAR_T *q = end;
 
3348
 
 
3349
                        while (p > pad_ptr)
 
3350
                          *--q = *--p;
 
3351
                        for (; pad > 0; pad--)
 
3352
                          *p++ = '0';
 
3353
                      }
 
3354
                    else
 
3355
                      {
 
3356
                        /* Pad with spaces on the left.  */
 
3357
                        DCHAR_T *q = end;
 
3358
 
 
3359
                        while (p > tmp)
 
3360
                          *--q = *--p;
 
3361
                        for (; pad > 0; pad--)
 
3362
                          *p++ = ' ';
 
3363
                      }
 
3364
 
 
3365
                    p = end;
 
3366
                  }
 
3367
 
 
3368
                {
 
3369
                  size_t count = p - tmp;
 
3370
 
 
3371
                  if (count >= tmp_length)
 
3372
                    /* tmp_length was incorrectly calculated - fix the
 
3373
                       code above!  */
 
3374
                    abort ();
 
3375
 
 
3376
                  /* Make room for the result.  */
 
3377
                  if (count >= allocated - length)
 
3378
                    {
 
3379
                      size_t n = xsum (length, count);
 
3380
 
 
3381
                      ENSURE_ALLOCATION (n);
 
3382
                    }
 
3383
 
 
3384
                  /* Append the result.  */
 
3385
                  memcpy (result + length, tmp, count * sizeof (DCHAR_T));
 
3386
                  if (tmp != tmpbuf)
 
3387
                    free (tmp);
 
3388
                  length += count;
 
3389
                }
 
3390
              }
 
3391
#endif
 
3392
#if (NEED_PRINTF_INFINITE_DOUBLE || NEED_PRINTF_DOUBLE || NEED_PRINTF_INFINITE_LONG_DOUBLE || NEED_PRINTF_LONG_DOUBLE) && !defined IN_LIBINTL
 
3393
            else if ((dp->conversion == 'f' || dp->conversion == 'F'
 
3394
                      || dp->conversion == 'e' || dp->conversion == 'E'
 
3395
                      || dp->conversion == 'g' || dp->conversion == 'G'
 
3396
                      || dp->conversion == 'a' || dp->conversion == 'A')
 
3397
                     && (0
 
3398
# if NEED_PRINTF_DOUBLE
 
3399
                         || a.arg[dp->arg_index].type == TYPE_DOUBLE
 
3400
# elif NEED_PRINTF_INFINITE_DOUBLE
 
3401
                         || (a.arg[dp->arg_index].type == TYPE_DOUBLE
 
3402
                             /* The systems (mingw) which produce wrong output
 
3403
                                for Inf, -Inf, and NaN also do so for -0.0.
 
3404
                                Therefore we treat this case here as well.  */
 
3405
                             && is_infinite_or_zero (a.arg[dp->arg_index].a.a_double))
 
3406
# endif
 
3407
# if NEED_PRINTF_LONG_DOUBLE
 
3408
                         || a.arg[dp->arg_index].type == TYPE_LONGDOUBLE
 
3409
# elif NEED_PRINTF_INFINITE_LONG_DOUBLE
 
3410
                         || (a.arg[dp->arg_index].type == TYPE_LONGDOUBLE
 
3411
                             /* Some systems produce wrong output for Inf,
 
3412
                                -Inf, and NaN.  Some systems in this category
 
3413
                                (IRIX 5.3) also do so for -0.0.  Therefore we
 
3414
                                treat this case here as well.  */
 
3415
                             && is_infinite_or_zerol (a.arg[dp->arg_index].a.a_longdouble))
 
3416
# endif
 
3417
                        ))
 
3418
              {
 
3419
# if (NEED_PRINTF_DOUBLE || NEED_PRINTF_INFINITE_DOUBLE) && (NEED_PRINTF_LONG_DOUBLE || NEED_PRINTF_INFINITE_LONG_DOUBLE)
 
3420
                arg_type type = a.arg[dp->arg_index].type;
 
3421
# endif
 
3422
                int flags = dp->flags;
 
3423
                int has_width;
 
3424
                size_t width;
 
3425
                int has_precision;
 
3426
                size_t precision;
 
3427
                size_t tmp_length;
 
3428
                DCHAR_T tmpbuf[700];
 
3429
                DCHAR_T *tmp;
 
3430
                DCHAR_T *pad_ptr;
 
3431
                DCHAR_T *p;
 
3432
 
 
3433
                has_width = 0;
 
3434
                width = 0;
 
3435
                if (dp->width_start != dp->width_end)
 
3436
                  {
 
3437
                    if (dp->width_arg_index != ARG_NONE)
 
3438
                      {
 
3439
                        int arg;
 
3440
 
 
3441
                        if (!(a.arg[dp->width_arg_index].type == TYPE_INT))
 
3442
                          abort ();
 
3443
                        arg = a.arg[dp->width_arg_index].a.a_int;
 
3444
                        if (arg < 0)
 
3445
                          {
 
3446
                            /* "A negative field width is taken as a '-' flag
 
3447
                                followed by a positive field width."  */
 
3448
                            flags |= FLAG_LEFT;
 
3449
                            width = (unsigned int) (-arg);
 
3450
                          }
 
3451
                        else
 
3452
                          width = arg;
 
3453
                      }
 
3454
                    else
 
3455
                      {
 
3456
                        const FCHAR_T *digitp = dp->width_start;
 
3457
 
 
3458
                        do
 
3459
                          width = xsum (xtimes (width, 10), *digitp++ - '0');
 
3460
                        while (digitp != dp->width_end);
 
3461
                      }
 
3462
                    has_width = 1;
 
3463
                  }
 
3464
 
 
3465
                has_precision = 0;
 
3466
                precision = 0;
 
3467
                if (dp->precision_start != dp->precision_end)
 
3468
                  {
 
3469
                    if (dp->precision_arg_index != ARG_NONE)
 
3470
                      {
 
3471
                        int arg;
 
3472
 
 
3473
                        if (!(a.arg[dp->precision_arg_index].type == TYPE_INT))
 
3474
                          abort ();
 
3475
                        arg = a.arg[dp->precision_arg_index].a.a_int;
 
3476
                        /* "A negative precision is taken as if the precision
 
3477
                            were omitted."  */
 
3478
                        if (arg >= 0)
 
3479
                          {
 
3480
                            precision = arg;
 
3481
                            has_precision = 1;
 
3482
                          }
 
3483
                      }
 
3484
                    else
 
3485
                      {
 
3486
                        const FCHAR_T *digitp = dp->precision_start + 1;
 
3487
 
 
3488
                        precision = 0;
 
3489
                        while (digitp != dp->precision_end)
 
3490
                          precision = xsum (xtimes (precision, 10), *digitp++ - '0');
 
3491
                        has_precision = 1;
 
3492
                      }
 
3493
                  }
 
3494
 
 
3495
                /* POSIX specifies the default precision to be 6 for %f, %F,
 
3496
                   %e, %E, but not for %g, %G.  Implementations appear to use
 
3497
                   the same default precision also for %g, %G.  But for %a, %A,
 
3498
                   the default precision is 0.  */
 
3499
                if (!has_precision)
 
3500
                  if (!(dp->conversion == 'a' || dp->conversion == 'A'))
 
3501
                    precision = 6;
 
3502
 
 
3503
                /* Allocate a temporary buffer of sufficient size.  */
 
3504
# if NEED_PRINTF_DOUBLE && NEED_PRINTF_LONG_DOUBLE
 
3505
                tmp_length = (type == TYPE_LONGDOUBLE ? LDBL_DIG + 1 : DBL_DIG + 1);
 
3506
# elif NEED_PRINTF_INFINITE_DOUBLE && NEED_PRINTF_LONG_DOUBLE
 
3507
                tmp_length = (type == TYPE_LONGDOUBLE ? LDBL_DIG + 1 : 0);
 
3508
# elif NEED_PRINTF_LONG_DOUBLE
 
3509
                tmp_length = LDBL_DIG + 1;
 
3510
# elif NEED_PRINTF_DOUBLE
 
3511
                tmp_length = DBL_DIG + 1;
 
3512
# else
 
3513
                tmp_length = 0;
 
3514
# endif
 
3515
                if (tmp_length < precision)
 
3516
                  tmp_length = precision;
 
3517
# if NEED_PRINTF_LONG_DOUBLE
 
3518
#  if NEED_PRINTF_DOUBLE || NEED_PRINTF_INFINITE_DOUBLE
 
3519
                if (type == TYPE_LONGDOUBLE)
 
3520
#  endif
 
3521
                  if (dp->conversion == 'f' || dp->conversion == 'F')
 
3522
                    {
 
3523
                      long double arg = a.arg[dp->arg_index].a.a_longdouble;
 
3524
                      if (!(isnanl (arg) || arg + arg == arg))
 
3525
                        {
 
3526
                          /* arg is finite and nonzero.  */
 
3527
                          int exponent = floorlog10l (arg < 0 ? -arg : arg);
 
3528
                          if (exponent >= 0 && tmp_length < exponent + precision)
 
3529
                            tmp_length = exponent + precision;
 
3530
                        }
 
3531
                    }
 
3532
# endif
 
3533
# if NEED_PRINTF_DOUBLE
 
3534
#  if NEED_PRINTF_LONG_DOUBLE || NEED_PRINTF_INFINITE_LONG_DOUBLE
 
3535
                if (type == TYPE_DOUBLE)
 
3536
#  endif
 
3537
                  if (dp->conversion == 'f' || dp->conversion == 'F')
 
3538
                    {
 
3539
                      double arg = a.arg[dp->arg_index].a.a_double;
 
3540
                      if (!(isnand (arg) || arg + arg == arg))
 
3541
                        {
 
3542
                          /* arg is finite and nonzero.  */
 
3543
                          int exponent = floorlog10 (arg < 0 ? -arg : arg);
 
3544
                          if (exponent >= 0 && tmp_length < exponent + precision)
 
3545
                            tmp_length = exponent + precision;
 
3546
                        }
 
3547
                    }
 
3548
# endif
 
3549
                /* Account for sign, decimal point etc. */
 
3550
                tmp_length = xsum (tmp_length, 12);
 
3551
 
 
3552
                if (tmp_length < width)
 
3553
                  tmp_length = width;
 
3554
 
 
3555
                tmp_length = xsum (tmp_length, 1); /* account for trailing NUL */
 
3556
 
 
3557
                if (tmp_length <= sizeof (tmpbuf) / sizeof (DCHAR_T))
 
3558
                  tmp = tmpbuf;
 
3559
                else
 
3560
                  {
 
3561
                    size_t tmp_memsize = xtimes (tmp_length, sizeof (DCHAR_T));
 
3562
 
 
3563
                    if (size_overflow_p (tmp_memsize))
 
3564
                      /* Overflow, would lead to out of memory.  */
 
3565
                      goto out_of_memory;
 
3566
                    tmp = (DCHAR_T *) malloc (tmp_memsize);
 
3567
                    if (tmp == NULL)
 
3568
                      /* Out of memory.  */
 
3569
                      goto out_of_memory;
 
3570
                  }
 
3571
 
 
3572
                pad_ptr = NULL;
 
3573
                p = tmp;
 
3574
 
 
3575
# if NEED_PRINTF_LONG_DOUBLE || NEED_PRINTF_INFINITE_LONG_DOUBLE
 
3576
#  if NEED_PRINTF_DOUBLE || NEED_PRINTF_INFINITE_DOUBLE
 
3577
                if (type == TYPE_LONGDOUBLE)
 
3578
#  endif
 
3579
                  {
 
3580
                    long double arg = a.arg[dp->arg_index].a.a_longdouble;
 
3581
 
 
3582
                    if (isnanl (arg))
 
3583
                      {
 
3584
                        if (dp->conversion >= 'A' && dp->conversion <= 'Z')
 
3585
                          {
 
3586
                            *p++ = 'N'; *p++ = 'A'; *p++ = 'N';
 
3587
                          }
 
3588
                        else
 
3589
                          {
 
3590
                            *p++ = 'n'; *p++ = 'a'; *p++ = 'n';
 
3591
                          }
 
3592
                      }
 
3593
                    else
 
3594
                      {
 
3595
                        int sign = 0;
 
3596
                        DECL_LONG_DOUBLE_ROUNDING
 
3597
 
 
3598
                        BEGIN_LONG_DOUBLE_ROUNDING ();
 
3599
 
 
3600
                        if (signbit (arg)) /* arg < 0.0L or negative zero */
 
3601
                          {
 
3602
                            sign = -1;
 
3603
                            arg = -arg;
 
3604
                          }
 
3605
 
 
3606
                        if (sign < 0)
 
3607
                          *p++ = '-';
 
3608
                        else if (flags & FLAG_SHOWSIGN)
 
3609
                          *p++ = '+';
 
3610
                        else if (flags & FLAG_SPACE)
 
3611
                          *p++ = ' ';
 
3612
 
 
3613
                        if (arg > 0.0L && arg + arg == arg)
 
3614
                          {
 
3615
                            if (dp->conversion >= 'A' && dp->conversion <= 'Z')
 
3616
                              {
 
3617
                                *p++ = 'I'; *p++ = 'N'; *p++ = 'F';
 
3618
                              }
 
3619
                            else
 
3620
                              {
 
3621
                                *p++ = 'i'; *p++ = 'n'; *p++ = 'f';
 
3622
                              }
 
3623
                          }
 
3624
                        else
 
3625
                          {
 
3626
#  if NEED_PRINTF_LONG_DOUBLE
 
3627
                            pad_ptr = p;
 
3628
 
 
3629
                            if (dp->conversion == 'f' || dp->conversion == 'F')
 
3630
                              {
 
3631
                                char *digits;
 
3632
                                size_t ndigits;
 
3633
 
 
3634
                                digits =
 
3635
                                  scale10_round_decimal_long_double (arg, precision);
 
3636
                                if (digits == NULL)
 
3637
                                  {
 
3638
                                    END_LONG_DOUBLE_ROUNDING ();
 
3639
                                    goto out_of_memory;
 
3640
                                  }
 
3641
                                ndigits = strlen (digits);
 
3642
 
 
3643
                                if (ndigits > precision)
 
3644
                                  do
 
3645
                                    {
 
3646
                                      --ndigits;
 
3647
                                      *p++ = digits[ndigits];
 
3648
                                    }
 
3649
                                  while (ndigits > precision);
 
3650
                                else
 
3651
                                  *p++ = '0';
 
3652
                                /* Here ndigits <= precision.  */
 
3653
                                if ((flags & FLAG_ALT) || precision > 0)
 
3654
                                  {
 
3655
                                    *p++ = decimal_point_char ();
 
3656
                                    for (; precision > ndigits; precision--)
 
3657
                                      *p++ = '0';
 
3658
                                    while (ndigits > 0)
 
3659
                                      {
 
3660
                                        --ndigits;
 
3661
                                        *p++ = digits[ndigits];
 
3662
                                      }
 
3663
                                  }
 
3664
 
 
3665
                                free (digits);
 
3666
                              }
 
3667
                            else if (dp->conversion == 'e' || dp->conversion == 'E')
 
3668
                              {
 
3669
                                int exponent;
 
3670
 
 
3671
                                if (arg == 0.0L)
 
3672
                                  {
 
3673
                                    exponent = 0;
 
3674
                                    *p++ = '0';
 
3675
                                    if ((flags & FLAG_ALT) || precision > 0)
 
3676
                                      {
 
3677
                                        *p++ = decimal_point_char ();
 
3678
                                        for (; precision > 0; precision--)
 
3679
                                          *p++ = '0';
 
3680
                                      }
 
3681
                                  }
 
3682
                                else
 
3683
                                  {
 
3684
                                    /* arg > 0.0L.  */
 
3685
                                    int adjusted;
 
3686
                                    char *digits;
 
3687
                                    size_t ndigits;
 
3688
 
 
3689
                                    exponent = floorlog10l (arg);
 
3690
                                    adjusted = 0;
 
3691
                                    for (;;)
 
3692
                                      {
 
3693
                                        digits =
 
3694
                                          scale10_round_decimal_long_double (arg,
 
3695
                                                                             (int)precision - exponent);
 
3696
                                        if (digits == NULL)
 
3697
                                          {
 
3698
                                            END_LONG_DOUBLE_ROUNDING ();
 
3699
                                            goto out_of_memory;
 
3700
                                          }
 
3701
                                        ndigits = strlen (digits);
 
3702
 
 
3703
                                        if (ndigits == precision + 1)
 
3704
                                          break;
 
3705
                                        if (ndigits < precision
 
3706
                                            || ndigits > precision + 2)
 
3707
                                          /* The exponent was not guessed
 
3708
                                             precisely enough.  */
 
3709
                                          abort ();
 
3710
                                        if (adjusted)
 
3711
                                          /* None of two values of exponent is
 
3712
                                             the right one.  Prevent an endless
 
3713
                                             loop.  */
 
3714
                                          abort ();
 
3715
                                        free (digits);
 
3716
                                        if (ndigits == precision)
 
3717
                                          exponent -= 1;
 
3718
                                        else
 
3719
                                          exponent += 1;
 
3720
                                        adjusted = 1;
 
3721
                                      }
 
3722
                                    /* Here ndigits = precision+1.  */
 
3723
                                    if (is_borderline (digits, precision))
 
3724
                                      {
 
3725
                                        /* Maybe the exponent guess was too high
 
3726
                                           and a smaller exponent can be reached
 
3727
                                           by turning a 10...0 into 9...9x.  */
 
3728
                                        char *digits2 =
 
3729
                                          scale10_round_decimal_long_double (arg,
 
3730
                                                                             (int)precision - exponent + 1);
 
3731
                                        if (digits2 == NULL)
 
3732
                                          {
 
3733
                                            free (digits);
 
3734
                                            END_LONG_DOUBLE_ROUNDING ();
 
3735
                                            goto out_of_memory;
 
3736
                                          }
 
3737
                                        if (strlen (digits2) == precision + 1)
 
3738
                                          {
 
3739
                                            free (digits);
 
3740
                                            digits = digits2;
 
3741
                                            exponent -= 1;
 
3742
                                          }
 
3743
                                        else
 
3744
                                          free (digits2);
 
3745
                                      }
 
3746
                                    /* Here ndigits = precision+1.  */
 
3747
 
 
3748
                                    *p++ = digits[--ndigits];
 
3749
                                    if ((flags & FLAG_ALT) || precision > 0)
 
3750
                                      {
 
3751
                                        *p++ = decimal_point_char ();
 
3752
                                        while (ndigits > 0)
 
3753
                                          {
 
3754
                                            --ndigits;
 
3755
                                            *p++ = digits[ndigits];
 
3756
                                          }
 
3757
                                      }
 
3758
 
 
3759
                                    free (digits);
 
3760
                                  }
 
3761
 
 
3762
                                *p++ = dp->conversion; /* 'e' or 'E' */
 
3763
#   if WIDE_CHAR_VERSION
 
3764
                                {
 
3765
                                  static const wchar_t decimal_format[] =
 
3766
                                    { '%', '+', '.', '2', 'd', '\0' };
 
3767
                                  SNPRINTF (p, 6 + 1, decimal_format, exponent);
 
3768
                                }
 
3769
                                while (*p != '\0')
 
3770
                                  p++;
 
3771
#   else
 
3772
                                if (sizeof (DCHAR_T) == 1)
 
3773
                                  {
 
3774
                                    sprintf ((char *) p, "%+.2d", exponent);
 
3775
                                    while (*p != '\0')
 
3776
                                      p++;
 
3777
                                  }
 
3778
                                else
 
3779
                                  {
 
3780
                                    char expbuf[6 + 1];
 
3781
                                    const char *ep;
 
3782
                                    sprintf (expbuf, "%+.2d", exponent);
 
3783
                                    for (ep = expbuf; (*p = *ep) != '\0'; ep++)
 
3784
                                      p++;
 
3785
                                  }
 
3786
#   endif
 
3787
                              }
 
3788
                            else if (dp->conversion == 'g' || dp->conversion == 'G')
 
3789
                              {
 
3790
                                if (precision == 0)
 
3791
                                  precision = 1;
 
3792
                                /* precision >= 1.  */
 
3793
 
 
3794
                                if (arg == 0.0L)
 
3795
                                  /* The exponent is 0, >= -4, < precision.
 
3796
                                     Use fixed-point notation.  */
 
3797
                                  {
 
3798
                                    size_t ndigits = precision;
 
3799
                                    /* Number of trailing zeroes that have to be
 
3800
                                       dropped.  */
 
3801
                                    size_t nzeroes =
 
3802
                                      (flags & FLAG_ALT ? 0 : precision - 1);
 
3803
 
 
3804
                                    --ndigits;
 
3805
                                    *p++ = '0';
 
3806
                                    if ((flags & FLAG_ALT) || ndigits > nzeroes)
 
3807
                                      {
 
3808
                                        *p++ = decimal_point_char ();
 
3809
                                        while (ndigits > nzeroes)
 
3810
                                          {
 
3811
                                            --ndigits;
 
3812
                                            *p++ = '0';
 
3813
                                          }
 
3814
                                      }
 
3815
                                  }
 
3816
                                else
 
3817
                                  {
 
3818
                                    /* arg > 0.0L.  */
 
3819
                                    int exponent;
 
3820
                                    int adjusted;
 
3821
                                    char *digits;
 
3822
                                    size_t ndigits;
 
3823
                                    size_t nzeroes;
 
3824
 
 
3825
                                    exponent = floorlog10l (arg);
 
3826
                                    adjusted = 0;
 
3827
                                    for (;;)
 
3828
                                      {
 
3829
                                        digits =
 
3830
                                          scale10_round_decimal_long_double (arg,
 
3831
                                                                             (int)(precision - 1) - exponent);
 
3832
                                        if (digits == NULL)
 
3833
                                          {
 
3834
                                            END_LONG_DOUBLE_ROUNDING ();
 
3835
                                            goto out_of_memory;
 
3836
                                          }
 
3837
                                        ndigits = strlen (digits);
 
3838
 
 
3839
                                        if (ndigits == precision)
 
3840
                                          break;
 
3841
                                        if (ndigits < precision - 1
 
3842
                                            || ndigits > precision + 1)
 
3843
                                          /* The exponent was not guessed
 
3844
                                             precisely enough.  */
 
3845
                                          abort ();
 
3846
                                        if (adjusted)
 
3847
                                          /* None of two values of exponent is
 
3848
                                             the right one.  Prevent an endless
 
3849
                                             loop.  */
 
3850
                                          abort ();
 
3851
                                        free (digits);
 
3852
                                        if (ndigits < precision)
 
3853
                                          exponent -= 1;
 
3854
                                        else
 
3855
                                          exponent += 1;
 
3856
                                        adjusted = 1;
 
3857
                                      }
 
3858
                                    /* Here ndigits = precision.  */
 
3859
                                    if (is_borderline (digits, precision - 1))
 
3860
                                      {
 
3861
                                        /* Maybe the exponent guess was too high
 
3862
                                           and a smaller exponent can be reached
 
3863
                                           by turning a 10...0 into 9...9x.  */
 
3864
                                        char *digits2 =
 
3865
                                          scale10_round_decimal_long_double (arg,
 
3866
                                                                             (int)(precision - 1) - exponent + 1);
 
3867
                                        if (digits2 == NULL)
 
3868
                                          {
 
3869
                                            free (digits);
 
3870
                                            END_LONG_DOUBLE_ROUNDING ();
 
3871
                                            goto out_of_memory;
 
3872
                                          }
 
3873
                                        if (strlen (digits2) == precision)
 
3874
                                          {
 
3875
                                            free (digits);
 
3876
                                            digits = digits2;
 
3877
                                            exponent -= 1;
 
3878
                                          }
 
3879
                                        else
 
3880
                                          free (digits2);
 
3881
                                      }
 
3882
                                    /* Here ndigits = precision.  */
 
3883
 
 
3884
                                    /* Determine the number of trailing zeroes
 
3885
                                       that have to be dropped.  */
 
3886
                                    nzeroes = 0;
 
3887
                                    if ((flags & FLAG_ALT) == 0)
 
3888
                                      while (nzeroes < ndigits
 
3889
                                             && digits[nzeroes] == '0')
 
3890
                                        nzeroes++;
 
3891
 
 
3892
                                    /* The exponent is now determined.  */
 
3893
                                    if (exponent >= -4
 
3894
                                        && exponent < (long)precision)
 
3895
                                      {
 
3896
                                        /* Fixed-point notation:
 
3897
                                           max(exponent,0)+1 digits, then the
 
3898
                                           decimal point, then the remaining
 
3899
                                           digits without trailing zeroes.  */
 
3900
                                        if (exponent >= 0)
 
3901
                                          {
 
3902
                                            size_t count = exponent + 1;
 
3903
                                            /* Note: count <= precision = ndigits.  */
 
3904
                                            for (; count > 0; count--)
 
3905
                                              *p++ = digits[--ndigits];
 
3906
                                            if ((flags & FLAG_ALT) || ndigits > nzeroes)
 
3907
                                              {
 
3908
                                                *p++ = decimal_point_char ();
 
3909
                                                while (ndigits > nzeroes)
 
3910
                                                  {
 
3911
                                                    --ndigits;
 
3912
                                                    *p++ = digits[ndigits];
 
3913
                                                  }
 
3914
                                              }
 
3915
                                          }
 
3916
                                        else
 
3917
                                          {
 
3918
                                            size_t count = -exponent - 1;
 
3919
                                            *p++ = '0';
 
3920
                                            *p++ = decimal_point_char ();
 
3921
                                            for (; count > 0; count--)
 
3922
                                              *p++ = '0';
 
3923
                                            while (ndigits > nzeroes)
 
3924
                                              {
 
3925
                                                --ndigits;
 
3926
                                                *p++ = digits[ndigits];
 
3927
                                              }
 
3928
                                          }
 
3929
                                      }
 
3930
                                    else
 
3931
                                      {
 
3932
                                        /* Exponential notation.  */
 
3933
                                        *p++ = digits[--ndigits];
 
3934
                                        if ((flags & FLAG_ALT) || ndigits > nzeroes)
 
3935
                                          {
 
3936
                                            *p++ = decimal_point_char ();
 
3937
                                            while (ndigits > nzeroes)
 
3938
                                              {
 
3939
                                                --ndigits;
 
3940
                                                *p++ = digits[ndigits];
 
3941
                                              }
 
3942
                                          }
 
3943
                                        *p++ = dp->conversion - 'G' + 'E'; /* 'e' or 'E' */
 
3944
#   if WIDE_CHAR_VERSION
 
3945
                                        {
 
3946
                                          static const wchar_t decimal_format[] =
 
3947
                                            { '%', '+', '.', '2', 'd', '\0' };
 
3948
                                          SNPRINTF (p, 6 + 1, decimal_format, exponent);
 
3949
                                        }
 
3950
                                        while (*p != '\0')
 
3951
                                          p++;
 
3952
#   else
 
3953
                                        if (sizeof (DCHAR_T) == 1)
 
3954
                                          {
 
3955
                                            sprintf ((char *) p, "%+.2d", exponent);
 
3956
                                            while (*p != '\0')
 
3957
                                              p++;
 
3958
                                          }
 
3959
                                        else
 
3960
                                          {
 
3961
                                            char expbuf[6 + 1];
 
3962
                                            const char *ep;
 
3963
                                            sprintf (expbuf, "%+.2d", exponent);
 
3964
                                            for (ep = expbuf; (*p = *ep) != '\0'; ep++)
 
3965
                                              p++;
 
3966
                                          }
 
3967
#   endif
 
3968
                                      }
 
3969
 
 
3970
                                    free (digits);
 
3971
                                  }
 
3972
                              }
 
3973
                            else
 
3974
                              abort ();
 
3975
#  else
 
3976
                            /* arg is finite.  */
 
3977
                            if (!(arg == 0.0L))
 
3978
                              abort ();
 
3979
 
 
3980
                            pad_ptr = p;
 
3981
 
 
3982
                            if (dp->conversion == 'f' || dp->conversion == 'F')
 
3983
                              {
 
3984
                                *p++ = '0';
 
3985
                                if ((flags & FLAG_ALT) || precision > 0)
 
3986
                                  {
 
3987
                                    *p++ = decimal_point_char ();
 
3988
                                    for (; precision > 0; precision--)
 
3989
                                      *p++ = '0';
 
3990
                                  }
 
3991
                              }
 
3992
                            else if (dp->conversion == 'e' || dp->conversion == 'E')
 
3993
                              {
 
3994
                                *p++ = '0';
 
3995
                                if ((flags & FLAG_ALT) || precision > 0)
 
3996
                                  {
 
3997
                                    *p++ = decimal_point_char ();
 
3998
                                    for (; precision > 0; precision--)
 
3999
                                      *p++ = '0';
 
4000
                                  }
 
4001
                                *p++ = dp->conversion; /* 'e' or 'E' */
 
4002
                                *p++ = '+';
 
4003
                                *p++ = '0';
 
4004
                                *p++ = '0';
 
4005
                              }
 
4006
                            else if (dp->conversion == 'g' || dp->conversion == 'G')
 
4007
                              {
 
4008
                                *p++ = '0';
 
4009
                                if (flags & FLAG_ALT)
 
4010
                                  {
 
4011
                                    size_t ndigits =
 
4012
                                      (precision > 0 ? precision - 1 : 0);
 
4013
                                    *p++ = decimal_point_char ();
 
4014
                                    for (; ndigits > 0; --ndigits)
 
4015
                                      *p++ = '0';
 
4016
                                  }
 
4017
                              }
 
4018
                            else if (dp->conversion == 'a' || dp->conversion == 'A')
 
4019
                              {
 
4020
                                *p++ = '0';
 
4021
                                *p++ = dp->conversion - 'A' + 'X';
 
4022
                                pad_ptr = p;
 
4023
                                *p++ = '0';
 
4024
                                if ((flags & FLAG_ALT) || precision > 0)
 
4025
                                  {
 
4026
                                    *p++ = decimal_point_char ();
 
4027
                                    for (; precision > 0; precision--)
 
4028
                                      *p++ = '0';
 
4029
                                  }
 
4030
                                *p++ = dp->conversion - 'A' + 'P';
 
4031
                                *p++ = '+';
 
4032
                                *p++ = '0';
 
4033
                              }
 
4034
                            else
 
4035
                              abort ();
 
4036
#  endif
 
4037
                          }
 
4038
 
 
4039
                        END_LONG_DOUBLE_ROUNDING ();
 
4040
                      }
 
4041
                  }
 
4042
#  if NEED_PRINTF_DOUBLE || NEED_PRINTF_INFINITE_DOUBLE
 
4043
                else
 
4044
#  endif
 
4045
# endif
 
4046
# if NEED_PRINTF_DOUBLE || NEED_PRINTF_INFINITE_DOUBLE
 
4047
                  {
 
4048
                    double arg = a.arg[dp->arg_index].a.a_double;
 
4049
 
 
4050
                    if (isnand (arg))
 
4051
                      {
 
4052
                        if (dp->conversion >= 'A' && dp->conversion <= 'Z')
 
4053
                          {
 
4054
                            *p++ = 'N'; *p++ = 'A'; *p++ = 'N';
 
4055
                          }
 
4056
                        else
 
4057
                          {
 
4058
                            *p++ = 'n'; *p++ = 'a'; *p++ = 'n';
 
4059
                          }
 
4060
                      }
 
4061
                    else
 
4062
                      {
 
4063
                        int sign = 0;
 
4064
 
 
4065
                        if (signbit (arg)) /* arg < 0.0 or negative zero */
 
4066
                          {
 
4067
                            sign = -1;
 
4068
                            arg = -arg;
 
4069
                          }
 
4070
 
 
4071
                        if (sign < 0)
 
4072
                          *p++ = '-';
 
4073
                        else if (flags & FLAG_SHOWSIGN)
 
4074
                          *p++ = '+';
 
4075
                        else if (flags & FLAG_SPACE)
 
4076
                          *p++ = ' ';
 
4077
 
 
4078
                        if (arg > 0.0 && arg + arg == arg)
 
4079
                          {
 
4080
                            if (dp->conversion >= 'A' && dp->conversion <= 'Z')
 
4081
                              {
 
4082
                                *p++ = 'I'; *p++ = 'N'; *p++ = 'F';
 
4083
                              }
 
4084
                            else
 
4085
                              {
 
4086
                                *p++ = 'i'; *p++ = 'n'; *p++ = 'f';
 
4087
                              }
 
4088
                          }
 
4089
                        else
 
4090
                          {
 
4091
#  if NEED_PRINTF_DOUBLE
 
4092
                            pad_ptr = p;
 
4093
 
 
4094
                            if (dp->conversion == 'f' || dp->conversion == 'F')
 
4095
                              {
 
4096
                                char *digits;
 
4097
                                size_t ndigits;
 
4098
 
 
4099
                                digits =
 
4100
                                  scale10_round_decimal_double (arg, precision);
 
4101
                                if (digits == NULL)
 
4102
                                  goto out_of_memory;
 
4103
                                ndigits = strlen (digits);
 
4104
 
 
4105
                                if (ndigits > precision)
 
4106
                                  do
 
4107
                                    {
 
4108
                                      --ndigits;
 
4109
                                      *p++ = digits[ndigits];
 
4110
                                    }
 
4111
                                  while (ndigits > precision);
 
4112
                                else
 
4113
                                  *p++ = '0';
 
4114
                                /* Here ndigits <= precision.  */
 
4115
                                if ((flags & FLAG_ALT) || precision > 0)
 
4116
                                  {
 
4117
                                    *p++ = decimal_point_char ();
 
4118
                                    for (; precision > ndigits; precision--)
 
4119
                                      *p++ = '0';
 
4120
                                    while (ndigits > 0)
 
4121
                                      {
 
4122
                                        --ndigits;
 
4123
                                        *p++ = digits[ndigits];
 
4124
                                      }
 
4125
                                  }
 
4126
 
 
4127
                                free (digits);
 
4128
                              }
 
4129
                            else if (dp->conversion == 'e' || dp->conversion == 'E')
 
4130
                              {
 
4131
                                int exponent;
 
4132
 
 
4133
                                if (arg == 0.0)
 
4134
                                  {
 
4135
                                    exponent = 0;
 
4136
                                    *p++ = '0';
 
4137
                                    if ((flags & FLAG_ALT) || precision > 0)
 
4138
                                      {
 
4139
                                        *p++ = decimal_point_char ();
 
4140
                                        for (; precision > 0; precision--)
 
4141
                                          *p++ = '0';
 
4142
                                      }
 
4143
                                  }
 
4144
                                else
 
4145
                                  {
 
4146
                                    /* arg > 0.0.  */
 
4147
                                    int adjusted;
 
4148
                                    char *digits;
 
4149
                                    size_t ndigits;
 
4150
 
 
4151
                                    exponent = floorlog10 (arg);
 
4152
                                    adjusted = 0;
 
4153
                                    for (;;)
 
4154
                                      {
 
4155
                                        digits =
 
4156
                                          scale10_round_decimal_double (arg,
 
4157
                                                                        (int)precision - exponent);
 
4158
                                        if (digits == NULL)
 
4159
                                          goto out_of_memory;
 
4160
                                        ndigits = strlen (digits);
 
4161
 
 
4162
                                        if (ndigits == precision + 1)
 
4163
                                          break;
 
4164
                                        if (ndigits < precision
 
4165
                                            || ndigits > precision + 2)
 
4166
                                          /* The exponent was not guessed
 
4167
                                             precisely enough.  */
 
4168
                                          abort ();
 
4169
                                        if (adjusted)
 
4170
                                          /* None of two values of exponent is
 
4171
                                             the right one.  Prevent an endless
 
4172
                                             loop.  */
 
4173
                                          abort ();
 
4174
                                        free (digits);
 
4175
                                        if (ndigits == precision)
 
4176
                                          exponent -= 1;
 
4177
                                        else
 
4178
                                          exponent += 1;
 
4179
                                        adjusted = 1;
 
4180
                                      }
 
4181
                                    /* Here ndigits = precision+1.  */
 
4182
                                    if (is_borderline (digits, precision))
 
4183
                                      {
 
4184
                                        /* Maybe the exponent guess was too high
 
4185
                                           and a smaller exponent can be reached
 
4186
                                           by turning a 10...0 into 9...9x.  */
 
4187
                                        char *digits2 =
 
4188
                                          scale10_round_decimal_double (arg,
 
4189
                                                                        (int)precision - exponent + 1);
 
4190
                                        if (digits2 == NULL)
 
4191
                                          {
 
4192
                                            free (digits);
 
4193
                                            goto out_of_memory;
 
4194
                                          }
 
4195
                                        if (strlen (digits2) == precision + 1)
 
4196
                                          {
 
4197
                                            free (digits);
 
4198
                                            digits = digits2;
 
4199
                                            exponent -= 1;
 
4200
                                          }
 
4201
                                        else
 
4202
                                          free (digits2);
 
4203
                                      }
 
4204
                                    /* Here ndigits = precision+1.  */
 
4205
 
 
4206
                                    *p++ = digits[--ndigits];
 
4207
                                    if ((flags & FLAG_ALT) || precision > 0)
 
4208
                                      {
 
4209
                                        *p++ = decimal_point_char ();
 
4210
                                        while (ndigits > 0)
 
4211
                                          {
 
4212
                                            --ndigits;
 
4213
                                            *p++ = digits[ndigits];
 
4214
                                          }
 
4215
                                      }
 
4216
 
 
4217
                                    free (digits);
 
4218
                                  }
 
4219
 
 
4220
                                *p++ = dp->conversion; /* 'e' or 'E' */
 
4221
#   if WIDE_CHAR_VERSION
 
4222
                                {
 
4223
                                  static const wchar_t decimal_format[] =
 
4224
                                    /* Produce the same number of exponent digits
 
4225
                                       as the native printf implementation.  */
 
4226
#    if (defined _WIN32 || defined __WIN32__) && ! defined __CYGWIN__
 
4227
                                    { '%', '+', '.', '3', 'd', '\0' };
 
4228
#    else
 
4229
                                    { '%', '+', '.', '2', 'd', '\0' };
 
4230
#    endif
 
4231
                                  SNPRINTF (p, 6 + 1, decimal_format, exponent);
 
4232
                                }
 
4233
                                while (*p != '\0')
 
4234
                                  p++;
 
4235
#   else
 
4236
                                {
 
4237
                                  static const char decimal_format[] =
 
4238
                                    /* Produce the same number of exponent digits
 
4239
                                       as the native printf implementation.  */
 
4240
#    if (defined _WIN32 || defined __WIN32__) && ! defined __CYGWIN__
 
4241
                                    "%+.3d";
 
4242
#    else
 
4243
                                    "%+.2d";
 
4244
#    endif
 
4245
                                  if (sizeof (DCHAR_T) == 1)
 
4246
                                    {
 
4247
                                      sprintf ((char *) p, decimal_format, exponent);
 
4248
                                      while (*p != '\0')
 
4249
                                        p++;
 
4250
                                    }
 
4251
                                  else
 
4252
                                    {
 
4253
                                      char expbuf[6 + 1];
 
4254
                                      const char *ep;
 
4255
                                      sprintf (expbuf, decimal_format, exponent);
 
4256
                                      for (ep = expbuf; (*p = *ep) != '\0'; ep++)
 
4257
                                        p++;
 
4258
                                    }
 
4259
                                }
 
4260
#   endif
 
4261
                              }
 
4262
                            else if (dp->conversion == 'g' || dp->conversion == 'G')
 
4263
                              {
 
4264
                                if (precision == 0)
 
4265
                                  precision = 1;
 
4266
                                /* precision >= 1.  */
 
4267
 
 
4268
                                if (arg == 0.0)
 
4269
                                  /* The exponent is 0, >= -4, < precision.
 
4270
                                     Use fixed-point notation.  */
 
4271
                                  {
 
4272
                                    size_t ndigits = precision;
 
4273
                                    /* Number of trailing zeroes that have to be
 
4274
                                       dropped.  */
 
4275
                                    size_t nzeroes =
 
4276
                                      (flags & FLAG_ALT ? 0 : precision - 1);
 
4277
 
 
4278
                                    --ndigits;
 
4279
                                    *p++ = '0';
 
4280
                                    if ((flags & FLAG_ALT) || ndigits > nzeroes)
 
4281
                                      {
 
4282
                                        *p++ = decimal_point_char ();
 
4283
                                        while (ndigits > nzeroes)
 
4284
                                          {
 
4285
                                            --ndigits;
 
4286
                                            *p++ = '0';
 
4287
                                          }
 
4288
                                      }
 
4289
                                  }
 
4290
                                else
 
4291
                                  {
 
4292
                                    /* arg > 0.0.  */
 
4293
                                    int exponent;
 
4294
                                    int adjusted;
 
4295
                                    char *digits;
 
4296
                                    size_t ndigits;
 
4297
                                    size_t nzeroes;
 
4298
 
 
4299
                                    exponent = floorlog10 (arg);
 
4300
                                    adjusted = 0;
 
4301
                                    for (;;)
 
4302
                                      {
 
4303
                                        digits =
 
4304
                                          scale10_round_decimal_double (arg,
 
4305
                                                                        (int)(precision - 1) - exponent);
 
4306
                                        if (digits == NULL)
 
4307
                                          goto out_of_memory;
 
4308
                                        ndigits = strlen (digits);
 
4309
 
 
4310
                                        if (ndigits == precision)
 
4311
                                          break;
 
4312
                                        if (ndigits < precision - 1
 
4313
                                            || ndigits > precision + 1)
 
4314
                                          /* The exponent was not guessed
 
4315
                                             precisely enough.  */
 
4316
                                          abort ();
 
4317
                                        if (adjusted)
 
4318
                                          /* None of two values of exponent is
 
4319
                                             the right one.  Prevent an endless
 
4320
                                             loop.  */
 
4321
                                          abort ();
 
4322
                                        free (digits);
 
4323
                                        if (ndigits < precision)
 
4324
                                          exponent -= 1;
 
4325
                                        else
 
4326
                                          exponent += 1;
 
4327
                                        adjusted = 1;
 
4328
                                      }
 
4329
                                    /* Here ndigits = precision.  */
 
4330
                                    if (is_borderline (digits, precision - 1))
 
4331
                                      {
 
4332
                                        /* Maybe the exponent guess was too high
 
4333
                                           and a smaller exponent can be reached
 
4334
                                           by turning a 10...0 into 9...9x.  */
 
4335
                                        char *digits2 =
 
4336
                                          scale10_round_decimal_double (arg,
 
4337
                                                                        (int)(precision - 1) - exponent + 1);
 
4338
                                        if (digits2 == NULL)
 
4339
                                          {
 
4340
                                            free (digits);
 
4341
                                            goto out_of_memory;
 
4342
                                          }
 
4343
                                        if (strlen (digits2) == precision)
 
4344
                                          {
 
4345
                                            free (digits);
 
4346
                                            digits = digits2;
 
4347
                                            exponent -= 1;
 
4348
                                          }
 
4349
                                        else
 
4350
                                          free (digits2);
 
4351
                                      }
 
4352
                                    /* Here ndigits = precision.  */
 
4353
 
 
4354
                                    /* Determine the number of trailing zeroes
 
4355
                                       that have to be dropped.  */
 
4356
                                    nzeroes = 0;
 
4357
                                    if ((flags & FLAG_ALT) == 0)
 
4358
                                      while (nzeroes < ndigits
 
4359
                                             && digits[nzeroes] == '0')
 
4360
                                        nzeroes++;
 
4361
 
 
4362
                                    /* The exponent is now determined.  */
 
4363
                                    if (exponent >= -4
 
4364
                                        && exponent < (long)precision)
 
4365
                                      {
 
4366
                                        /* Fixed-point notation:
 
4367
                                           max(exponent,0)+1 digits, then the
 
4368
                                           decimal point, then the remaining
 
4369
                                           digits without trailing zeroes.  */
 
4370
                                        if (exponent >= 0)
 
4371
                                          {
 
4372
                                            size_t count = exponent + 1;
 
4373
                                            /* Note: count <= precision = ndigits.  */
 
4374
                                            for (; count > 0; count--)
 
4375
                                              *p++ = digits[--ndigits];
 
4376
                                            if ((flags & FLAG_ALT) || ndigits > nzeroes)
 
4377
                                              {
 
4378
                                                *p++ = decimal_point_char ();
 
4379
                                                while (ndigits > nzeroes)
 
4380
                                                  {
 
4381
                                                    --ndigits;
 
4382
                                                    *p++ = digits[ndigits];
 
4383
                                                  }
 
4384
                                              }
 
4385
                                          }
 
4386
                                        else
 
4387
                                          {
 
4388
                                            size_t count = -exponent - 1;
 
4389
                                            *p++ = '0';
 
4390
                                            *p++ = decimal_point_char ();
 
4391
                                            for (; count > 0; count--)
 
4392
                                              *p++ = '0';
 
4393
                                            while (ndigits > nzeroes)
 
4394
                                              {
 
4395
                                                --ndigits;
 
4396
                                                *p++ = digits[ndigits];
 
4397
                                              }
 
4398
                                          }
 
4399
                                      }
 
4400
                                    else
 
4401
                                      {
 
4402
                                        /* Exponential notation.  */
 
4403
                                        *p++ = digits[--ndigits];
 
4404
                                        if ((flags & FLAG_ALT) || ndigits > nzeroes)
 
4405
                                          {
 
4406
                                            *p++ = decimal_point_char ();
 
4407
                                            while (ndigits > nzeroes)
 
4408
                                              {
 
4409
                                                --ndigits;
 
4410
                                                *p++ = digits[ndigits];
 
4411
                                              }
 
4412
                                          }
 
4413
                                        *p++ = dp->conversion - 'G' + 'E'; /* 'e' or 'E' */
 
4414
#   if WIDE_CHAR_VERSION
 
4415
                                        {
 
4416
                                          static const wchar_t decimal_format[] =
 
4417
                                            /* Produce the same number of exponent digits
 
4418
                                               as the native printf implementation.  */
 
4419
#    if (defined _WIN32 || defined __WIN32__) && ! defined __CYGWIN__
 
4420
                                            { '%', '+', '.', '3', 'd', '\0' };
 
4421
#    else
 
4422
                                            { '%', '+', '.', '2', 'd', '\0' };
 
4423
#    endif
 
4424
                                          SNPRINTF (p, 6 + 1, decimal_format, exponent);
 
4425
                                        }
 
4426
                                        while (*p != '\0')
 
4427
                                          p++;
 
4428
#   else
 
4429
                                        {
 
4430
                                          static const char decimal_format[] =
 
4431
                                            /* Produce the same number of exponent digits
 
4432
                                               as the native printf implementation.  */
 
4433
#    if (defined _WIN32 || defined __WIN32__) && ! defined __CYGWIN__
 
4434
                                            "%+.3d";
 
4435
#    else
 
4436
                                            "%+.2d";
 
4437
#    endif
 
4438
                                          if (sizeof (DCHAR_T) == 1)
 
4439
                                            {
 
4440
                                              sprintf ((char *) p, decimal_format, exponent);
 
4441
                                              while (*p != '\0')
 
4442
                                                p++;
 
4443
                                            }
 
4444
                                          else
 
4445
                                            {
 
4446
                                              char expbuf[6 + 1];
 
4447
                                              const char *ep;
 
4448
                                              sprintf (expbuf, decimal_format, exponent);
 
4449
                                              for (ep = expbuf; (*p = *ep) != '\0'; ep++)
 
4450
                                                p++;
 
4451
                                            }
 
4452
                                        }
 
4453
#   endif
 
4454
                                      }
 
4455
 
 
4456
                                    free (digits);
 
4457
                                  }
 
4458
                              }
 
4459
                            else
 
4460
                              abort ();
 
4461
#  else
 
4462
                            /* arg is finite.  */
 
4463
                            if (!(arg == 0.0))
 
4464
                              abort ();
 
4465
 
 
4466
                            pad_ptr = p;
 
4467
 
 
4468
                            if (dp->conversion == 'f' || dp->conversion == 'F')
 
4469
                              {
 
4470
                                *p++ = '0';
 
4471
                                if ((flags & FLAG_ALT) || precision > 0)
 
4472
                                  {
 
4473
                                    *p++ = decimal_point_char ();
 
4474
                                    for (; precision > 0; precision--)
 
4475
                                      *p++ = '0';
 
4476
                                  }
 
4477
                              }
 
4478
                            else if (dp->conversion == 'e' || dp->conversion == 'E')
 
4479
                              {
 
4480
                                *p++ = '0';
 
4481
                                if ((flags & FLAG_ALT) || precision > 0)
 
4482
                                  {
 
4483
                                    *p++ = decimal_point_char ();
 
4484
                                    for (; precision > 0; precision--)
 
4485
                                      *p++ = '0';
 
4486
                                  }
 
4487
                                *p++ = dp->conversion; /* 'e' or 'E' */
 
4488
                                *p++ = '+';
 
4489
                                /* Produce the same number of exponent digits as
 
4490
                                   the native printf implementation.  */
 
4491
#   if (defined _WIN32 || defined __WIN32__) && ! defined __CYGWIN__
 
4492
                                *p++ = '0';
 
4493
#   endif
 
4494
                                *p++ = '0';
 
4495
                                *p++ = '0';
 
4496
                              }
 
4497
                            else if (dp->conversion == 'g' || dp->conversion == 'G')
 
4498
                              {
 
4499
                                *p++ = '0';
 
4500
                                if (flags & FLAG_ALT)
 
4501
                                  {
 
4502
                                    size_t ndigits =
 
4503
                                      (precision > 0 ? precision - 1 : 0);
 
4504
                                    *p++ = decimal_point_char ();
 
4505
                                    for (; ndigits > 0; --ndigits)
 
4506
                                      *p++ = '0';
 
4507
                                  }
 
4508
                              }
 
4509
                            else
 
4510
                              abort ();
 
4511
#  endif
 
4512
                          }
 
4513
                      }
 
4514
                  }
 
4515
# endif
 
4516
 
 
4517
                /* The generated string now extends from tmp to p, with the
 
4518
                   zero padding insertion point being at pad_ptr.  */
 
4519
                if (has_width && p - tmp < width)
 
4520
                  {
 
4521
                    size_t pad = width - (p - tmp);
 
4522
                    DCHAR_T *end = p + pad;
 
4523
 
 
4524
                    if (flags & FLAG_LEFT)
 
4525
                      {
 
4526
                        /* Pad with spaces on the right.  */
 
4527
                        for (; pad > 0; pad--)
 
4528
                          *p++ = ' ';
 
4529
                      }
 
4530
                    else if ((flags & FLAG_ZERO) && pad_ptr != NULL)
 
4531
                      {
 
4532
                        /* Pad with zeroes.  */
 
4533
                        DCHAR_T *q = end;
 
4534
 
 
4535
                        while (p > pad_ptr)
 
4536
                          *--q = *--p;
 
4537
                        for (; pad > 0; pad--)
 
4538
                          *p++ = '0';
 
4539
                      }
 
4540
                    else
 
4541
                      {
 
4542
                        /* Pad with spaces on the left.  */
 
4543
                        DCHAR_T *q = end;
 
4544
 
 
4545
                        while (p > tmp)
 
4546
                          *--q = *--p;
 
4547
                        for (; pad > 0; pad--)
 
4548
                          *p++ = ' ';
 
4549
                      }
 
4550
 
 
4551
                    p = end;
 
4552
                  }
 
4553
 
 
4554
                {
 
4555
                  size_t count = p - tmp;
 
4556
 
 
4557
                  if (count >= tmp_length)
 
4558
                    /* tmp_length was incorrectly calculated - fix the
 
4559
                       code above!  */
 
4560
                    abort ();
 
4561
 
 
4562
                  /* Make room for the result.  */
 
4563
                  if (count >= allocated - length)
 
4564
                    {
 
4565
                      size_t n = xsum (length, count);
 
4566
 
 
4567
                      ENSURE_ALLOCATION (n);
 
4568
                    }
 
4569
 
 
4570
                  /* Append the result.  */
 
4571
                  memcpy (result + length, tmp, count * sizeof (DCHAR_T));
 
4572
                  if (tmp != tmpbuf)
 
4573
                    free (tmp);
 
4574
                  length += count;
 
4575
                }
 
4576
              }
 
4577
#endif
 
4578
            else
 
4579
              {
 
4580
                arg_type type = a.arg[dp->arg_index].type;
 
4581
                int flags = dp->flags;
 
4582
#if !USE_SNPRINTF || !HAVE_SNPRINTF_RETVAL_C99 || !DCHAR_IS_TCHAR || ENABLE_UNISTDIO || NEED_PRINTF_FLAG_LEFTADJUST || NEED_PRINTF_FLAG_ZERO || NEED_PRINTF_UNBOUNDED_PRECISION
 
4583
                int has_width;
 
4584
                size_t width;
 
4585
#endif
 
4586
#if !USE_SNPRINTF || !HAVE_SNPRINTF_RETVAL_C99 || NEED_PRINTF_UNBOUNDED_PRECISION
 
4587
                int has_precision;
 
4588
                size_t precision;
 
4589
#endif
 
4590
#if NEED_PRINTF_UNBOUNDED_PRECISION
 
4591
                int prec_ourselves;
 
4592
#else
 
4593
#               define prec_ourselves 0
 
4594
#endif
 
4595
#if NEED_PRINTF_FLAG_LEFTADJUST
 
4596
#               define pad_ourselves 1
 
4597
#elif !DCHAR_IS_TCHAR || ENABLE_UNISTDIO || NEED_PRINTF_FLAG_ZERO || NEED_PRINTF_UNBOUNDED_PRECISION
 
4598
                int pad_ourselves;
 
4599
#else
 
4600
#               define pad_ourselves 0
 
4601
#endif
 
4602
                TCHAR_T *fbp;
 
4603
                unsigned int prefix_count;
 
4604
                int prefixes[2] IF_LINT (= { 0 });
 
4605
                int orig_errno;
 
4606
#if !USE_SNPRINTF
 
4607
                size_t tmp_length;
 
4608
                TCHAR_T tmpbuf[700];
 
4609
                TCHAR_T *tmp;
 
4610
#endif
 
4611
 
 
4612
#if !USE_SNPRINTF || !HAVE_SNPRINTF_RETVAL_C99 || !DCHAR_IS_TCHAR || ENABLE_UNISTDIO || NEED_PRINTF_FLAG_LEFTADJUST || NEED_PRINTF_FLAG_ZERO || NEED_PRINTF_UNBOUNDED_PRECISION
 
4613
                has_width = 0;
 
4614
                width = 0;
 
4615
                if (dp->width_start != dp->width_end)
 
4616
                  {
 
4617
                    if (dp->width_arg_index != ARG_NONE)
 
4618
                      {
 
4619
                        int arg;
 
4620
 
 
4621
                        if (!(a.arg[dp->width_arg_index].type == TYPE_INT))
 
4622
                          abort ();
 
4623
                        arg = a.arg[dp->width_arg_index].a.a_int;
 
4624
                        if (arg < 0)
 
4625
                          {
 
4626
                            /* "A negative field width is taken as a '-' flag
 
4627
                                followed by a positive field width."  */
 
4628
                            flags |= FLAG_LEFT;
 
4629
                            width = (unsigned int) (-arg);
 
4630
                          }
 
4631
                        else
 
4632
                          width = arg;
 
4633
                      }
 
4634
                    else
 
4635
                      {
 
4636
                        const FCHAR_T *digitp = dp->width_start;
 
4637
 
 
4638
                        do
 
4639
                          width = xsum (xtimes (width, 10), *digitp++ - '0');
 
4640
                        while (digitp != dp->width_end);
 
4641
                      }
 
4642
                    has_width = 1;
 
4643
                  }
 
4644
#endif
 
4645
 
 
4646
#if !USE_SNPRINTF || !HAVE_SNPRINTF_RETVAL_C99 || NEED_PRINTF_UNBOUNDED_PRECISION
 
4647
                has_precision = 0;
 
4648
                precision = 6;
 
4649
                if (dp->precision_start != dp->precision_end)
 
4650
                  {
 
4651
                    if (dp->precision_arg_index != ARG_NONE)
 
4652
                      {
 
4653
                        int arg;
 
4654
 
 
4655
                        if (!(a.arg[dp->precision_arg_index].type == TYPE_INT))
 
4656
                          abort ();
 
4657
                        arg = a.arg[dp->precision_arg_index].a.a_int;
 
4658
                        /* "A negative precision is taken as if the precision
 
4659
                            were omitted."  */
 
4660
                        if (arg >= 0)
 
4661
                          {
 
4662
                            precision = arg;
 
4663
                            has_precision = 1;
 
4664
                          }
 
4665
                      }
 
4666
                    else
 
4667
                      {
 
4668
                        const FCHAR_T *digitp = dp->precision_start + 1;
 
4669
 
 
4670
                        precision = 0;
 
4671
                        while (digitp != dp->precision_end)
 
4672
                          precision = xsum (xtimes (precision, 10), *digitp++ - '0');
 
4673
                        has_precision = 1;
 
4674
                      }
 
4675
                  }
 
4676
#endif
 
4677
 
 
4678
                /* Decide whether to handle the precision ourselves.  */
 
4679
#if NEED_PRINTF_UNBOUNDED_PRECISION
 
4680
                switch (dp->conversion)
 
4681
                  {
 
4682
                  case 'd': case 'i': case 'u':
 
4683
                  case 'o':
 
4684
                  case 'x': case 'X': case 'p':
 
4685
                    prec_ourselves = has_precision && (precision > 0);
 
4686
                    break;
 
4687
                  default:
 
4688
                    prec_ourselves = 0;
 
4689
                    break;
 
4690
                  }
 
4691
#endif
 
4692
 
 
4693
                /* Decide whether to perform the padding ourselves.  */
 
4694
#if !NEED_PRINTF_FLAG_LEFTADJUST && (!DCHAR_IS_TCHAR || ENABLE_UNISTDIO || NEED_PRINTF_FLAG_ZERO || NEED_PRINTF_UNBOUNDED_PRECISION)
 
4695
                switch (dp->conversion)
 
4696
                  {
 
4697
# if !DCHAR_IS_TCHAR || ENABLE_UNISTDIO
 
4698
                  /* If we need conversion from TCHAR_T[] to DCHAR_T[], we need
 
4699
                     to perform the padding after this conversion.  Functions
 
4700
                     with unistdio extensions perform the padding based on
 
4701
                     character count rather than element count.  */
 
4702
                  case 'c': case 's':
 
4703
# endif
 
4704
# if NEED_PRINTF_FLAG_ZERO
 
4705
                  case 'f': case 'F': case 'e': case 'E': case 'g': case 'G':
 
4706
                  case 'a': case 'A':
 
4707
# endif
 
4708
                    pad_ourselves = 1;
 
4709
                    break;
 
4710
                  default:
 
4711
                    pad_ourselves = prec_ourselves;
 
4712
                    break;
 
4713
                  }
 
4714
#endif
 
4715
 
 
4716
#if !USE_SNPRINTF
 
4717
                /* Allocate a temporary buffer of sufficient size for calling
 
4718
                   sprintf.  */
 
4719
                tmp_length =
 
4720
                  MAX_ROOM_NEEDED (&a, dp->arg_index, dp->conversion, type,
 
4721
                                   flags, width, has_precision, precision,
 
4722
                                   pad_ourselves);
 
4723
 
 
4724
                if (tmp_length <= sizeof (tmpbuf) / sizeof (TCHAR_T))
 
4725
                  tmp = tmpbuf;
 
4726
                else
 
4727
                  {
 
4728
                    size_t tmp_memsize = xtimes (tmp_length, sizeof (TCHAR_T));
 
4729
 
 
4730
                    if (size_overflow_p (tmp_memsize))
 
4731
                      /* Overflow, would lead to out of memory.  */
 
4732
                      goto out_of_memory;
 
4733
                    tmp = (TCHAR_T *) malloc (tmp_memsize);
 
4734
                    if (tmp == NULL)
 
4735
                      /* Out of memory.  */
 
4736
                      goto out_of_memory;
 
4737
                  }
 
4738
#endif
 
4739
 
 
4740
                /* Construct the format string for calling snprintf or
 
4741
                   sprintf.  */
 
4742
                fbp = buf;
 
4743
                *fbp++ = '%';
 
4744
#if NEED_PRINTF_FLAG_GROUPING
 
4745
                /* The underlying implementation doesn't support the ' flag.
 
4746
                   Produce no grouping characters in this case; this is
 
4747
                   acceptable because the grouping is locale dependent.  */
 
4748
#else
 
4749
                if (flags & FLAG_GROUP)
 
4750
                  *fbp++ = '\'';
 
4751
#endif
 
4752
                if (flags & FLAG_LEFT)
 
4753
                  *fbp++ = '-';
 
4754
                if (flags & FLAG_SHOWSIGN)
 
4755
                  *fbp++ = '+';
 
4756
                if (flags & FLAG_SPACE)
 
4757
                  *fbp++ = ' ';
 
4758
                if (flags & FLAG_ALT)
 
4759
                  *fbp++ = '#';
 
4760
#if __GLIBC__ >= 2 && !defined __UCLIBC__
 
4761
                if (flags & FLAG_LOCALIZED)
 
4762
                  *fbp++ = 'I';
 
4763
#endif
 
4764
                if (!pad_ourselves)
 
4765
                  {
 
4766
                    if (flags & FLAG_ZERO)
 
4767
                      *fbp++ = '0';
 
4768
                    if (dp->width_start != dp->width_end)
 
4769
                      {
 
4770
                        size_t n = dp->width_end - dp->width_start;
 
4771
                        /* The width specification is known to consist only
 
4772
                           of standard ASCII characters.  */
 
4773
                        if (sizeof (FCHAR_T) == sizeof (TCHAR_T))
 
4774
                          {
 
4775
                            memcpy (fbp, dp->width_start, n * sizeof (TCHAR_T));
 
4776
                            fbp += n;
 
4777
                          }
 
4778
                        else
 
4779
                          {
 
4780
                            const FCHAR_T *mp = dp->width_start;
 
4781
                            do
 
4782
                              *fbp++ = (unsigned char) *mp++;
 
4783
                            while (--n > 0);
 
4784
                          }
 
4785
                      }
 
4786
                  }
 
4787
                if (!prec_ourselves)
 
4788
                  {
 
4789
                    if (dp->precision_start != dp->precision_end)
 
4790
                      {
 
4791
                        size_t n = dp->precision_end - dp->precision_start;
 
4792
                        /* The precision specification is known to consist only
 
4793
                           of standard ASCII characters.  */
 
4794
                        if (sizeof (FCHAR_T) == sizeof (TCHAR_T))
 
4795
                          {
 
4796
                            memcpy (fbp, dp->precision_start, n * sizeof (TCHAR_T));
 
4797
                            fbp += n;
 
4798
                          }
 
4799
                        else
 
4800
                          {
 
4801
                            const FCHAR_T *mp = dp->precision_start;
 
4802
                            do
 
4803
                              *fbp++ = (unsigned char) *mp++;
 
4804
                            while (--n > 0);
 
4805
                          }
 
4806
                      }
 
4807
                  }
 
4808
 
 
4809
                switch (type)
 
4810
                  {
 
4811
#if HAVE_LONG_LONG_INT
 
4812
                  case TYPE_LONGLONGINT:
 
4813
                  case TYPE_ULONGLONGINT:
 
4814
# if (defined _WIN32 || defined __WIN32__) && ! defined __CYGWIN__
 
4815
                    *fbp++ = 'I';
 
4816
                    *fbp++ = '6';
 
4817
                    *fbp++ = '4';
 
4818
                    break;
 
4819
# else
 
4820
                    *fbp++ = 'l';
 
4821
                    /*FALLTHROUGH*/
 
4822
# endif
 
4823
#endif
 
4824
                  case TYPE_LONGINT:
 
4825
                  case TYPE_ULONGINT:
 
4826
#if HAVE_WINT_T
 
4827
                  case TYPE_WIDE_CHAR:
 
4828
#endif
 
4829
#if HAVE_WCHAR_T
 
4830
                  case TYPE_WIDE_STRING:
 
4831
#endif
 
4832
                    *fbp++ = 'l';
 
4833
                    break;
 
4834
                  case TYPE_LONGDOUBLE:
 
4835
                    *fbp++ = 'L';
 
4836
                    break;
 
4837
                  default:
 
4838
                    break;
 
4839
                  }
 
4840
#if NEED_PRINTF_DIRECTIVE_F
 
4841
                if (dp->conversion == 'F')
 
4842
                  *fbp = 'f';
 
4843
                else
 
4844
#endif
 
4845
                  *fbp = dp->conversion;
 
4846
#if USE_SNPRINTF
 
4847
# if !(((__GLIBC__ > 2 || (__GLIBC__ == 2 && __GLIBC_MINOR__ >= 3)) && !defined __UCLIBC__) || ((defined _WIN32 || defined __WIN32__) && ! defined __CYGWIN__))
 
4848
                fbp[1] = '%';
 
4849
                fbp[2] = 'n';
 
4850
                fbp[3] = '\0';
 
4851
# else
 
4852
                /* On glibc2 systems from glibc >= 2.3 - probably also older
 
4853
                   ones - we know that snprintf's return value conforms to
 
4854
                   ISO C 99: the tests gl_SNPRINTF_RETVAL_C99 and
 
4855
                   gl_SNPRINTF_TRUNCATION_C99 pass.
 
4856
                   Therefore we can avoid using %n in this situation.
 
4857
                   On glibc2 systems from 2004-10-18 or newer, the use of %n
 
4858
                   in format strings in writable memory may crash the program
 
4859
                   (if compiled with _FORTIFY_SOURCE=2), so we should avoid it
 
4860
                   in this situation.  */
 
4861
                /* On native Win32 systems (such as mingw), we can avoid using
 
4862
                   %n because:
 
4863
                     - Although the gl_SNPRINTF_TRUNCATION_C99 test fails,
 
4864
                       snprintf does not write more than the specified number
 
4865
                       of bytes. (snprintf (buf, 3, "%d %d", 4567, 89) writes
 
4866
                       '4', '5', '6' into buf, not '4', '5', '\0'.)
 
4867
                     - Although the gl_SNPRINTF_RETVAL_C99 test fails, snprintf
 
4868
                       allows us to recognize the case of an insufficient
 
4869
                       buffer size: it returns -1 in this case.
 
4870
                   On native Win32 systems (such as mingw) where the OS is
 
4871
                   Windows Vista, the use of %n in format strings by default
 
4872
                   crashes the program. See
 
4873
                     <http://gcc.gnu.org/ml/gcc/2007-06/msg00122.html> and
 
4874
                     <http://msdn2.microsoft.com/en-us/library/ms175782(VS.80).aspx>
 
4875
                   So we should avoid %n in this situation.  */
 
4876
                fbp[1] = '\0';
 
4877
# endif
 
4878
#else
 
4879
                fbp[1] = '\0';
 
4880
#endif
 
4881
 
 
4882
                /* Construct the arguments for calling snprintf or sprintf.  */
 
4883
                prefix_count = 0;
 
4884
                if (!pad_ourselves && dp->width_arg_index != ARG_NONE)
 
4885
                  {
 
4886
                    if (!(a.arg[dp->width_arg_index].type == TYPE_INT))
 
4887
                      abort ();
 
4888
                    prefixes[prefix_count++] = a.arg[dp->width_arg_index].a.a_int;
 
4889
                  }
 
4890
                if (!prec_ourselves && dp->precision_arg_index != ARG_NONE)
 
4891
                  {
 
4892
                    if (!(a.arg[dp->precision_arg_index].type == TYPE_INT))
 
4893
                      abort ();
 
4894
                    prefixes[prefix_count++] = a.arg[dp->precision_arg_index].a.a_int;
 
4895
                  }
 
4896
 
 
4897
#if USE_SNPRINTF
 
4898
                /* The SNPRINTF result is appended after result[0..length].
 
4899
                   The latter is an array of DCHAR_T; SNPRINTF appends an
 
4900
                   array of TCHAR_T to it.  This is possible because
 
4901
                   sizeof (TCHAR_T) divides sizeof (DCHAR_T) and
 
4902
                   alignof (TCHAR_T) <= alignof (DCHAR_T).  */
 
4903
# define TCHARS_PER_DCHAR (sizeof (DCHAR_T) / sizeof (TCHAR_T))
 
4904
                /* Ensure that maxlen below will be >= 2.  Needed on BeOS,
 
4905
                   where an snprintf() with maxlen==1 acts like sprintf().  */
 
4906
                ENSURE_ALLOCATION (xsum (length,
 
4907
                                         (2 + TCHARS_PER_DCHAR - 1)
 
4908
                                         / TCHARS_PER_DCHAR));
 
4909
                /* Prepare checking whether snprintf returns the count
 
4910
                   via %n.  */
 
4911
                *(TCHAR_T *) (result + length) = '\0';
 
4912
#endif
 
4913
 
 
4914
                orig_errno = errno;
 
4915
 
 
4916
                for (;;)
 
4917
                  {
 
4918
                    int count = -1;
 
4919
 
 
4920
#if USE_SNPRINTF
 
4921
                    int retcount = 0;
 
4922
                    size_t maxlen = allocated - length;
 
4923
                    /* SNPRINTF can fail if its second argument is
 
4924
                       > INT_MAX.  */
 
4925
                    if (maxlen > INT_MAX / TCHARS_PER_DCHAR)
 
4926
                      maxlen = INT_MAX / TCHARS_PER_DCHAR;
 
4927
                    maxlen = maxlen * TCHARS_PER_DCHAR;
 
4928
# define SNPRINTF_BUF(arg) \
 
4929
                    switch (prefix_count)                                   \
 
4930
                      {                                                     \
 
4931
                      case 0:                                               \
 
4932
                        retcount = SNPRINTF ((TCHAR_T *) (result + length), \
 
4933
                                             maxlen, buf,                   \
 
4934
                                             arg, &count);                  \
 
4935
                        break;                                              \
 
4936
                      case 1:                                               \
 
4937
                        retcount = SNPRINTF ((TCHAR_T *) (result + length), \
 
4938
                                             maxlen, buf,                   \
 
4939
                                             prefixes[0], arg, &count);     \
 
4940
                        break;                                              \
 
4941
                      case 2:                                               \
 
4942
                        retcount = SNPRINTF ((TCHAR_T *) (result + length), \
 
4943
                                             maxlen, buf,                   \
 
4944
                                             prefixes[0], prefixes[1], arg, \
 
4945
                                             &count);                       \
 
4946
                        break;                                              \
 
4947
                      default:                                              \
 
4948
                        abort ();                                           \
 
4949
                      }
 
4950
#else
 
4951
# define SNPRINTF_BUF(arg) \
 
4952
                    switch (prefix_count)                                   \
 
4953
                      {                                                     \
 
4954
                      case 0:                                               \
 
4955
                        count = sprintf (tmp, buf, arg);                    \
 
4956
                        break;                                              \
 
4957
                      case 1:                                               \
 
4958
                        count = sprintf (tmp, buf, prefixes[0], arg);       \
 
4959
                        break;                                              \
 
4960
                      case 2:                                               \
 
4961
                        count = sprintf (tmp, buf, prefixes[0], prefixes[1],\
 
4962
                                         arg);                              \
 
4963
                        break;                                              \
 
4964
                      default:                                              \
 
4965
                        abort ();                                           \
 
4966
                      }
 
4967
#endif
 
4968
 
 
4969
                    errno = 0;
 
4970
                    switch (type)
 
4971
                      {
 
4972
                      case TYPE_SCHAR:
 
4973
                        {
 
4974
                          int arg = a.arg[dp->arg_index].a.a_schar;
 
4975
                          SNPRINTF_BUF (arg);
 
4976
                        }
 
4977
                        break;
 
4978
                      case TYPE_UCHAR:
 
4979
                        {
 
4980
                          unsigned int arg = a.arg[dp->arg_index].a.a_uchar;
 
4981
                          SNPRINTF_BUF (arg);
 
4982
                        }
 
4983
                        break;
 
4984
                      case TYPE_SHORT:
 
4985
                        {
 
4986
                          int arg = a.arg[dp->arg_index].a.a_short;
 
4987
                          SNPRINTF_BUF (arg);
 
4988
                        }
 
4989
                        break;
 
4990
                      case TYPE_USHORT:
 
4991
                        {
 
4992
                          unsigned int arg = a.arg[dp->arg_index].a.a_ushort;
 
4993
                          SNPRINTF_BUF (arg);
 
4994
                        }
 
4995
                        break;
 
4996
                      case TYPE_INT:
 
4997
                        {
 
4998
                          int arg = a.arg[dp->arg_index].a.a_int;
 
4999
                          SNPRINTF_BUF (arg);
 
5000
                        }
 
5001
                        break;
 
5002
                      case TYPE_UINT:
 
5003
                        {
 
5004
                          unsigned int arg = a.arg[dp->arg_index].a.a_uint;
 
5005
                          SNPRINTF_BUF (arg);
 
5006
                        }
 
5007
                        break;
 
5008
                      case TYPE_LONGINT:
 
5009
                        {
 
5010
                          long int arg = a.arg[dp->arg_index].a.a_longint;
 
5011
                          SNPRINTF_BUF (arg);
 
5012
                        }
 
5013
                        break;
 
5014
                      case TYPE_ULONGINT:
 
5015
                        {
 
5016
                          unsigned long int arg = a.arg[dp->arg_index].a.a_ulongint;
 
5017
                          SNPRINTF_BUF (arg);
 
5018
                        }
 
5019
                        break;
 
5020
#if HAVE_LONG_LONG_INT
 
5021
                      case TYPE_LONGLONGINT:
 
5022
                        {
 
5023
                          long long int arg = a.arg[dp->arg_index].a.a_longlongint;
 
5024
                          SNPRINTF_BUF (arg);
 
5025
                        }
 
5026
                        break;
 
5027
                      case TYPE_ULONGLONGINT:
 
5028
                        {
 
5029
                          unsigned long long int arg = a.arg[dp->arg_index].a.a_ulonglongint;
 
5030
                          SNPRINTF_BUF (arg);
 
5031
                        }
 
5032
                        break;
 
5033
#endif
 
5034
                      case TYPE_DOUBLE:
 
5035
                        {
 
5036
                          double arg = a.arg[dp->arg_index].a.a_double;
 
5037
                          SNPRINTF_BUF (arg);
 
5038
                        }
 
5039
                        break;
 
5040
                      case TYPE_LONGDOUBLE:
 
5041
                        {
 
5042
                          long double arg = a.arg[dp->arg_index].a.a_longdouble;
 
5043
                          SNPRINTF_BUF (arg);
 
5044
                        }
 
5045
                        break;
 
5046
                      case TYPE_CHAR:
 
5047
                        {
 
5048
                          int arg = a.arg[dp->arg_index].a.a_char;
 
5049
                          SNPRINTF_BUF (arg);
 
5050
                        }
 
5051
                        break;
 
5052
#if HAVE_WINT_T
 
5053
                      case TYPE_WIDE_CHAR:
 
5054
                        {
 
5055
                          wint_t arg = a.arg[dp->arg_index].a.a_wide_char;
 
5056
                          SNPRINTF_BUF (arg);
 
5057
                        }
 
5058
                        break;
 
5059
#endif
 
5060
                      case TYPE_STRING:
 
5061
                        {
 
5062
                          const char *arg = a.arg[dp->arg_index].a.a_string;
 
5063
                          SNPRINTF_BUF (arg);
 
5064
                        }
 
5065
                        break;
 
5066
#if HAVE_WCHAR_T
 
5067
                      case TYPE_WIDE_STRING:
 
5068
                        {
 
5069
                          const wchar_t *arg = a.arg[dp->arg_index].a.a_wide_string;
 
5070
                          SNPRINTF_BUF (arg);
 
5071
                        }
 
5072
                        break;
 
5073
#endif
 
5074
                      case TYPE_POINTER:
 
5075
                        {
 
5076
                          void *arg = a.arg[dp->arg_index].a.a_pointer;
 
5077
                          SNPRINTF_BUF (arg);
 
5078
                        }
 
5079
                        break;
 
5080
                      default:
 
5081
                        abort ();
 
5082
                      }
 
5083
 
 
5084
#if USE_SNPRINTF
 
5085
                    /* Portability: Not all implementations of snprintf()
 
5086
                       are ISO C 99 compliant.  Determine the number of
 
5087
                       bytes that snprintf() has produced or would have
 
5088
                       produced.  */
 
5089
                    if (count >= 0)
 
5090
                      {
 
5091
                        /* Verify that snprintf() has NUL-terminated its
 
5092
                           result.  */
 
5093
                        if (count < maxlen
 
5094
                            && ((TCHAR_T *) (result + length)) [count] != '\0')
 
5095
                          abort ();
 
5096
                        /* Portability hack.  */
 
5097
                        if (retcount > count)
 
5098
                          count = retcount;
 
5099
                      }
 
5100
                    else
 
5101
                      {
 
5102
                        /* snprintf() doesn't understand the '%n'
 
5103
                           directive.  */
 
5104
                        if (fbp[1] != '\0')
 
5105
                          {
 
5106
                            /* Don't use the '%n' directive; instead, look
 
5107
                               at the snprintf() return value.  */
 
5108
                            fbp[1] = '\0';
 
5109
                            continue;
 
5110
                          }
 
5111
                        else
 
5112
                          {
 
5113
                            /* Look at the snprintf() return value.  */
 
5114
                            if (retcount < 0)
 
5115
                              {
 
5116
# if !HAVE_SNPRINTF_RETVAL_C99
 
5117
                                /* HP-UX 10.20 snprintf() is doubly deficient:
 
5118
                                   It doesn't understand the '%n' directive,
 
5119
                                   *and* it returns -1 (rather than the length
 
5120
                                   that would have been required) when the
 
5121
                                   buffer is too small.
 
5122
                                   But a failure at this point can also come
 
5123
                                   from other reasons than a too small buffer,
 
5124
                                   such as an invalid wide string argument to
 
5125
                                   the %ls directive, or possibly an invalid
 
5126
                                   floating-point argument.  */
 
5127
                                size_t tmp_length =
 
5128
                                  MAX_ROOM_NEEDED (&a, dp->arg_index,
 
5129
                                                   dp->conversion, type, flags,
 
5130
                                                   width, has_precision,
 
5131
                                                   precision, pad_ourselves);
 
5132
 
 
5133
                                if (maxlen < tmp_length)
 
5134
                                  {
 
5135
                                    /* Make more room.  But try to do through
 
5136
                                       this reallocation only once.  */
 
5137
                                    size_t bigger_need =
 
5138
                                      xsum (length,
 
5139
                                            xsum (tmp_length,
 
5140
                                                  TCHARS_PER_DCHAR - 1)
 
5141
                                            / TCHARS_PER_DCHAR);
 
5142
                                    /* And always grow proportionally.
 
5143
                                       (There may be several arguments, each
 
5144
                                       needing a little more room than the
 
5145
                                       previous one.)  */
 
5146
                                    size_t bigger_need2 =
 
5147
                                      xsum (xtimes (allocated, 2), 12);
 
5148
                                    if (bigger_need < bigger_need2)
 
5149
                                      bigger_need = bigger_need2;
 
5150
                                    ENSURE_ALLOCATION (bigger_need);
 
5151
                                    continue;
 
5152
                                  }
 
5153
# endif
 
5154
                              }
 
5155
                            else
 
5156
                              count = retcount;
 
5157
                          }
 
5158
                      }
 
5159
#endif
 
5160
 
 
5161
                    /* Attempt to handle failure.  */
 
5162
                    if (count < 0)
 
5163
                      {
 
5164
                        /* SNPRINTF or sprintf failed.  Save and use the errno
 
5165
                           that it has set, if any.  */
 
5166
                        int saved_errno = errno;
 
5167
 
 
5168
                        if (!(result == resultbuf || result == NULL))
 
5169
                          free (result);
 
5170
                        if (buf_malloced != NULL)
 
5171
                          free (buf_malloced);
 
5172
                        CLEANUP ();
 
5173
                        errno =
 
5174
                          (saved_errno != 0
 
5175
                           ? saved_errno
 
5176
                           : (dp->conversion == 'c' || dp->conversion == 's'
 
5177
                              ? EILSEQ
 
5178
                              : EINVAL));
 
5179
                        return NULL;
 
5180
                      }
 
5181
 
 
5182
#if USE_SNPRINTF
 
5183
                    /* Handle overflow of the allocated buffer.
 
5184
                       If such an overflow occurs, a C99 compliant snprintf()
 
5185
                       returns a count >= maxlen.  However, a non-compliant
 
5186
                       snprintf() function returns only count = maxlen - 1.  To
 
5187
                       cover both cases, test whether count >= maxlen - 1.  */
 
5188
                    if ((unsigned int) count + 1 >= maxlen)
 
5189
                      {
 
5190
                        /* If maxlen already has attained its allowed maximum,
 
5191
                           allocating more memory will not increase maxlen.
 
5192
                           Instead of looping, bail out.  */
 
5193
                        if (maxlen == INT_MAX / TCHARS_PER_DCHAR)
 
5194
                          goto overflow;
 
5195
                        else
 
5196
                          {
 
5197
                            /* Need at least (count + 1) * sizeof (TCHAR_T)
 
5198
                               bytes.  (The +1 is for the trailing NUL.)
 
5199
                               But ask for (count + 2) * sizeof (TCHAR_T)
 
5200
                               bytes, so that in the next round, we likely get
 
5201
                                 maxlen > (unsigned int) count + 1
 
5202
                               and so we don't get here again.
 
5203
                               And allocate proportionally, to avoid looping
 
5204
                               eternally if snprintf() reports a too small
 
5205
                               count.  */
 
5206
                            size_t n =
 
5207
                              xmax (xsum (length,
 
5208
                                          ((unsigned int) count + 2
 
5209
                                           + TCHARS_PER_DCHAR - 1)
 
5210
                                          / TCHARS_PER_DCHAR),
 
5211
                                    xtimes (allocated, 2));
 
5212
 
 
5213
                            ENSURE_ALLOCATION (n);
 
5214
                            continue;
 
5215
                          }
 
5216
                      }
 
5217
#endif
 
5218
 
 
5219
#if NEED_PRINTF_UNBOUNDED_PRECISION
 
5220
                    if (prec_ourselves)
 
5221
                      {
 
5222
                        /* Handle the precision.  */
 
5223
                        TCHAR_T *prec_ptr =
 
5224
# if USE_SNPRINTF
 
5225
                          (TCHAR_T *) (result + length);
 
5226
# else
 
5227
                          tmp;
 
5228
# endif
 
5229
                        size_t prefix_count;
 
5230
                        size_t move;
 
5231
 
 
5232
                        prefix_count = 0;
 
5233
                        /* Put the additional zeroes after the sign.  */
 
5234
                        if (count >= 1
 
5235
                            && (*prec_ptr == '-' || *prec_ptr == '+'
 
5236
                                || *prec_ptr == ' '))
 
5237
                          prefix_count = 1;
 
5238
                        /* Put the additional zeroes after the 0x prefix if
 
5239
                           (flags & FLAG_ALT) || (dp->conversion == 'p').  */
 
5240
                        else if (count >= 2
 
5241
                                 && prec_ptr[0] == '0'
 
5242
                                 && (prec_ptr[1] == 'x' || prec_ptr[1] == 'X'))
 
5243
                          prefix_count = 2;
 
5244
 
 
5245
                        move = count - prefix_count;
 
5246
                        if (precision > move)
 
5247
                          {
 
5248
                            /* Insert zeroes.  */
 
5249
                            size_t insert = precision - move;
 
5250
                            TCHAR_T *prec_end;
 
5251
 
 
5252
# if USE_SNPRINTF
 
5253
                            size_t n =
 
5254
                              xsum (length,
 
5255
                                    (count + insert + TCHARS_PER_DCHAR - 1)
 
5256
                                    / TCHARS_PER_DCHAR);
 
5257
                            length += (count + TCHARS_PER_DCHAR - 1) / TCHARS_PER_DCHAR;
 
5258
                            ENSURE_ALLOCATION (n);
 
5259
                            length -= (count + TCHARS_PER_DCHAR - 1) / TCHARS_PER_DCHAR;
 
5260
                            prec_ptr = (TCHAR_T *) (result + length);
 
5261
# endif
 
5262
 
 
5263
                            prec_end = prec_ptr + count;
 
5264
                            prec_ptr += prefix_count;
 
5265
 
 
5266
                            while (prec_end > prec_ptr)
 
5267
                              {
 
5268
                                prec_end--;
 
5269
                                prec_end[insert] = prec_end[0];
 
5270
                              }
 
5271
 
 
5272
                            prec_end += insert;
 
5273
                            do
 
5274
                              *--prec_end = '0';
 
5275
                            while (prec_end > prec_ptr);
 
5276
 
 
5277
                            count += insert;
 
5278
                          }
 
5279
                      }
 
5280
#endif
 
5281
 
 
5282
#if !USE_SNPRINTF
 
5283
                    if (count >= tmp_length)
 
5284
                      /* tmp_length was incorrectly calculated - fix the
 
5285
                         code above!  */
 
5286
                      abort ();
 
5287
#endif
 
5288
 
 
5289
#if !DCHAR_IS_TCHAR
 
5290
                    /* Convert from TCHAR_T[] to DCHAR_T[].  */
 
5291
                    if (dp->conversion == 'c' || dp->conversion == 's')
 
5292
                      {
 
5293
                        /* type = TYPE_CHAR or TYPE_WIDE_CHAR or TYPE_STRING
 
5294
                           TYPE_WIDE_STRING.
 
5295
                           The result string is not certainly ASCII.  */
 
5296
                        const TCHAR_T *tmpsrc;
 
5297
                        DCHAR_T *tmpdst;
 
5298
                        size_t tmpdst_len;
 
5299
                        /* This code assumes that TCHAR_T is 'char'.  */
 
5300
                        verify (sizeof (TCHAR_T) == 1);
 
5301
# if USE_SNPRINTF
 
5302
                        tmpsrc = (TCHAR_T *) (result + length);
 
5303
# else
 
5304
                        tmpsrc = tmp;
 
5305
# endif
 
5306
                        tmpdst =
 
5307
                          DCHAR_CONV_FROM_ENCODING (locale_charset (),
 
5308
                                                    iconveh_question_mark,
 
5309
                                                    tmpsrc, count,
 
5310
                                                    NULL,
 
5311
                                                    NULL, &tmpdst_len);
 
5312
                        if (tmpdst == NULL)
 
5313
                          {
 
5314
                            int saved_errno = errno;
 
5315
                            if (!(result == resultbuf || result == NULL))
 
5316
                              free (result);
 
5317
                            if (buf_malloced != NULL)
 
5318
                              free (buf_malloced);
 
5319
                            CLEANUP ();
 
5320
                            errno = saved_errno;
 
5321
                            return NULL;
 
5322
                          }
 
5323
                        ENSURE_ALLOCATION (xsum (length, tmpdst_len));
 
5324
                        DCHAR_CPY (result + length, tmpdst, tmpdst_len);
 
5325
                        free (tmpdst);
 
5326
                        count = tmpdst_len;
 
5327
                      }
 
5328
                    else
 
5329
                      {
 
5330
                        /* The result string is ASCII.
 
5331
                           Simple 1:1 conversion.  */
 
5332
# if USE_SNPRINTF
 
5333
                        /* If sizeof (DCHAR_T) == sizeof (TCHAR_T), it's a
 
5334
                           no-op conversion, in-place on the array starting
 
5335
                           at (result + length).  */
 
5336
                        if (sizeof (DCHAR_T) != sizeof (TCHAR_T))
 
5337
# endif
 
5338
                          {
 
5339
                            const TCHAR_T *tmpsrc;
 
5340
                            DCHAR_T *tmpdst;
 
5341
                            size_t n;
 
5342
 
 
5343
# if USE_SNPRINTF
 
5344
                            if (result == resultbuf)
 
5345
                              {
 
5346
                                tmpsrc = (TCHAR_T *) (result + length);
 
5347
                                /* ENSURE_ALLOCATION will not move tmpsrc
 
5348
                                   (because it's part of resultbuf).  */
 
5349
                                ENSURE_ALLOCATION (xsum (length, count));
 
5350
                              }
 
5351
                            else
 
5352
                              {
 
5353
                                /* ENSURE_ALLOCATION will move the array
 
5354
                                   (because it uses realloc().  */
 
5355
                                ENSURE_ALLOCATION (xsum (length, count));
 
5356
                                tmpsrc = (TCHAR_T *) (result + length);
 
5357
                              }
 
5358
# else
 
5359
                            tmpsrc = tmp;
 
5360
                            ENSURE_ALLOCATION (xsum (length, count));
 
5361
# endif
 
5362
                            tmpdst = result + length;
 
5363
                            /* Copy backwards, because of overlapping.  */
 
5364
                            tmpsrc += count;
 
5365
                            tmpdst += count;
 
5366
                            for (n = count; n > 0; n--)
 
5367
                              *--tmpdst = (unsigned char) *--tmpsrc;
 
5368
                          }
 
5369
                      }
 
5370
#endif
 
5371
 
 
5372
#if DCHAR_IS_TCHAR && !USE_SNPRINTF
 
5373
                    /* Make room for the result.  */
 
5374
                    if (count > allocated - length)
 
5375
                      {
 
5376
                        /* Need at least count elements.  But allocate
 
5377
                           proportionally.  */
 
5378
                        size_t n =
 
5379
                          xmax (xsum (length, count), xtimes (allocated, 2));
 
5380
 
 
5381
                        ENSURE_ALLOCATION (n);
 
5382
                      }
 
5383
#endif
 
5384
 
 
5385
                    /* Here count <= allocated - length.  */
 
5386
 
 
5387
                    /* Perform padding.  */
 
5388
#if !DCHAR_IS_TCHAR || ENABLE_UNISTDIO || NEED_PRINTF_FLAG_LEFTADJUST || NEED_PRINTF_FLAG_ZERO || NEED_PRINTF_UNBOUNDED_PRECISION
 
5389
                    if (pad_ourselves && has_width)
 
5390
                      {
 
5391
                        size_t w;
 
5392
# if ENABLE_UNISTDIO
 
5393
                        /* Outside POSIX, it's preferrable to compare the width
 
5394
                           against the number of _characters_ of the converted
 
5395
                           value.  */
 
5396
                        w = DCHAR_MBSNLEN (result + length, count);
 
5397
# else
 
5398
                        /* The width is compared against the number of _bytes_
 
5399
                           of the converted value, says POSIX.  */
 
5400
                        w = count;
 
5401
# endif
 
5402
                        if (w < width)
 
5403
                          {
 
5404
                            size_t pad = width - w;
 
5405
 
 
5406
                            /* Make room for the result.  */
 
5407
                            if (xsum (count, pad) > allocated - length)
 
5408
                              {
 
5409
                                /* Need at least count + pad elements.  But
 
5410
                                   allocate proportionally.  */
 
5411
                                size_t n =
 
5412
                                  xmax (xsum3 (length, count, pad),
 
5413
                                        xtimes (allocated, 2));
 
5414
 
 
5415
# if USE_SNPRINTF
 
5416
                                length += count;
 
5417
                                ENSURE_ALLOCATION (n);
 
5418
                                length -= count;
 
5419
# else
 
5420
                                ENSURE_ALLOCATION (n);
 
5421
# endif
 
5422
                              }
 
5423
                            /* Here count + pad <= allocated - length.  */
 
5424
 
 
5425
                            {
 
5426
# if !DCHAR_IS_TCHAR || USE_SNPRINTF
 
5427
                              DCHAR_T * const rp = result + length;
 
5428
# else
 
5429
                              DCHAR_T * const rp = tmp;
 
5430
# endif
 
5431
                              DCHAR_T *p = rp + count;
 
5432
                              DCHAR_T *end = p + pad;
 
5433
                              DCHAR_T *pad_ptr;
 
5434
# if !DCHAR_IS_TCHAR || ENABLE_UNISTDIO
 
5435
                              if (dp->conversion == 'c'
 
5436
                                  || dp->conversion == 's')
 
5437
                                /* No zero-padding for string directives.  */
 
5438
                                pad_ptr = NULL;
 
5439
                              else
 
5440
# endif
 
5441
                                {
 
5442
                                  pad_ptr = (*rp == '-' ? rp + 1 : rp);
 
5443
                                  /* No zero-padding of "inf" and "nan".  */
 
5444
                                  if ((*pad_ptr >= 'A' && *pad_ptr <= 'Z')
 
5445
                                      || (*pad_ptr >= 'a' && *pad_ptr <= 'z'))
 
5446
                                    pad_ptr = NULL;
 
5447
                                }
 
5448
                              /* The generated string now extends from rp to p,
 
5449
                                 with the zero padding insertion point being at
 
5450
                                 pad_ptr.  */
 
5451
 
 
5452
                              count = count + pad; /* = end - rp */
 
5453
 
 
5454
                              if (flags & FLAG_LEFT)
 
5455
                                {
 
5456
                                  /* Pad with spaces on the right.  */
 
5457
                                  for (; pad > 0; pad--)
 
5458
                                    *p++ = ' ';
 
5459
                                }
 
5460
                              else if ((flags & FLAG_ZERO) && pad_ptr != NULL)
 
5461
                                {
 
5462
                                  /* Pad with zeroes.  */
 
5463
                                  DCHAR_T *q = end;
 
5464
 
 
5465
                                  while (p > pad_ptr)
 
5466
                                    *--q = *--p;
 
5467
                                  for (; pad > 0; pad--)
 
5468
                                    *p++ = '0';
 
5469
                                }
 
5470
                              else
 
5471
                                {
 
5472
                                  /* Pad with spaces on the left.  */
 
5473
                                  DCHAR_T *q = end;
 
5474
 
 
5475
                                  while (p > rp)
 
5476
                                    *--q = *--p;
 
5477
                                  for (; pad > 0; pad--)
 
5478
                                    *p++ = ' ';
 
5479
                                }
 
5480
                            }
 
5481
                          }
 
5482
                      }
 
5483
#endif
 
5484
 
 
5485
                    /* Here still count <= allocated - length.  */
 
5486
 
 
5487
#if !DCHAR_IS_TCHAR || USE_SNPRINTF
 
5488
                    /* The snprintf() result did fit.  */
 
5489
#else
 
5490
                    /* Append the sprintf() result.  */
 
5491
                    memcpy (result + length, tmp, count * sizeof (DCHAR_T));
 
5492
#endif
 
5493
#if !USE_SNPRINTF
 
5494
                    if (tmp != tmpbuf)
 
5495
                      free (tmp);
 
5496
#endif
 
5497
 
 
5498
#if NEED_PRINTF_DIRECTIVE_F
 
5499
                    if (dp->conversion == 'F')
 
5500
                      {
 
5501
                        /* Convert the %f result to upper case for %F.  */
 
5502
                        DCHAR_T *rp = result + length;
 
5503
                        size_t rc;
 
5504
                        for (rc = count; rc > 0; rc--, rp++)
 
5505
                          if (*rp >= 'a' && *rp <= 'z')
 
5506
                            *rp = *rp - 'a' + 'A';
 
5507
                      }
 
5508
#endif
 
5509
 
 
5510
                    length += count;
 
5511
                    break;
 
5512
                  }
 
5513
                errno = orig_errno;
 
5514
#undef pad_ourselves
 
5515
#undef prec_ourselves
 
5516
              }
 
5517
          }
 
5518
      }
 
5519
 
 
5520
    /* Add the final NUL.  */
 
5521
    ENSURE_ALLOCATION (xsum (length, 1));
 
5522
    result[length] = '\0';
 
5523
 
 
5524
    if (result != resultbuf && length + 1 < allocated)
 
5525
      {
 
5526
        /* Shrink the allocated memory if possible.  */
 
5527
        DCHAR_T *memory;
 
5528
 
 
5529
        memory = (DCHAR_T *) realloc (result, (length + 1) * sizeof (DCHAR_T));
 
5530
        if (memory != NULL)
 
5531
          result = memory;
 
5532
      }
 
5533
 
 
5534
    if (buf_malloced != NULL)
 
5535
      free (buf_malloced);
 
5536
    CLEANUP ();
 
5537
    *lengthp = length;
 
5538
    /* Note that we can produce a big string of a length > INT_MAX.  POSIX
 
5539
       says that snprintf() fails with errno = EOVERFLOW in this case, but
 
5540
       that's only because snprintf() returns an 'int'.  This function does
 
5541
       not have this limitation.  */
 
5542
    return result;
 
5543
 
 
5544
#if USE_SNPRINTF
 
5545
  overflow:
 
5546
    if (!(result == resultbuf || result == NULL))
 
5547
      free (result);
 
5548
    if (buf_malloced != NULL)
 
5549
      free (buf_malloced);
 
5550
    CLEANUP ();
 
5551
    errno = EOVERFLOW;
 
5552
    return NULL;
 
5553
#endif
 
5554
 
 
5555
  out_of_memory:
 
5556
    if (!(result == resultbuf || result == NULL))
 
5557
      free (result);
 
5558
    if (buf_malloced != NULL)
 
5559
      free (buf_malloced);
 
5560
  out_of_memory_1:
 
5561
    CLEANUP ();
 
5562
    errno = ENOMEM;
 
5563
    return NULL;
 
5564
  }
 
5565
}
 
5566
 
 
5567
#undef MAX_ROOM_NEEDED
 
5568
#undef TCHARS_PER_DCHAR
 
5569
#undef SNPRINTF
 
5570
#undef USE_SNPRINTF
 
5571
#undef DCHAR_SET
 
5572
#undef DCHAR_CPY
 
5573
#undef PRINTF_PARSE
 
5574
#undef DIRECTIVES
 
5575
#undef DIRECTIVE
 
5576
#undef DCHAR_IS_TCHAR
 
5577
#undef TCHAR_T
 
5578
#undef DCHAR_T
 
5579
#undef FCHAR_T
 
5580
#undef VASNPRINTF