Add x86 init-arch to nptl
[glibc.git] / stdio-common / vfscanf.c
blob343056769ebad7fe0a636f3e8eb8cd88b590f41e
1 /* Copyright (C) 1991-2013 Free Software Foundation, Inc.
2 This file is part of the GNU C Library.
4 The GNU C Library is free software; you can redistribute it and/or
5 modify it under the terms of the GNU Lesser General Public
6 License as published by the Free Software Foundation; either
7 version 2.1 of the License, or (at your option) any later version.
9 The GNU C Library is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 Lesser General Public License for more details.
14 You should have received a copy of the GNU Lesser General Public
15 License along with the GNU C Library; if not, see
16 <http://www.gnu.org/licenses/>. */
18 #include <assert.h>
19 #include <errno.h>
20 #include <limits.h>
21 #include <ctype.h>
22 #include <stdarg.h>
23 #include <stdbool.h>
24 #include <stdio.h>
25 #include <stdint.h>
26 #include <stdlib.h>
27 #include <string.h>
28 #include <wchar.h>
29 #include <wctype.h>
30 #include <bits/libc-lock.h>
31 #include <locale/localeinfo.h>
33 #ifdef __GNUC__
34 # define HAVE_LONGLONG
35 # define LONGLONG long long
36 #else
37 # define LONGLONG long
38 #endif
40 /* Determine whether we have to handle `long long' at all. */
41 #if LONG_MAX == LONG_LONG_MAX
42 # define need_longlong 0
43 #else
44 # define need_longlong 1
45 #endif
47 /* Determine whether we have to handle `long'. */
48 #if INT_MAX == LONG_MAX
49 # define need_long 0
50 #else
51 # define need_long 1
52 #endif
54 /* Those are flags in the conversion format. */
55 #define LONG 0x0001 /* l: long or double */
56 #define LONGDBL 0x0002 /* L: long long or long double */
57 #define SHORT 0x0004 /* h: short */
58 #define SUPPRESS 0x0008 /* *: suppress assignment */
59 #define POINTER 0x0010 /* weird %p pointer (`fake hex') */
60 #define NOSKIP 0x0020 /* do not skip blanks */
61 #define NUMBER_SIGNED 0x0040 /* signed integer */
62 #define GROUP 0x0080 /* ': group numbers */
63 #define GNU_MALLOC 0x0100 /* a: malloc strings */
64 #define CHAR 0x0200 /* hh: char */
65 #define I18N 0x0400 /* I: use locale's digits */
66 #define HEXA_FLOAT 0x0800 /* hexadecimal float */
67 #define READ_POINTER 0x1000 /* this is a pointer value */
68 #define POSIX_MALLOC 0x2000 /* m: malloc strings */
69 #define MALLOC (GNU_MALLOC | POSIX_MALLOC)
71 #include <locale/localeinfo.h>
72 #include <libioP.h>
73 #include <libio.h>
75 #undef va_list
76 #define va_list _IO_va_list
78 #ifdef COMPILE_WSCANF
79 # define ungetc(c, s) ((void) (c == WEOF \
80 || (--read_in, \
81 _IO_sputbackwc (s, c))))
82 # define ungetc_not_eof(c, s) ((void) (--read_in, \
83 _IO_sputbackwc (s, c)))
84 # define inchar() (c == WEOF ? ((errno = inchar_errno), WEOF) \
85 : ((c = _IO_getwc_unlocked (s)), \
86 (void) (c != WEOF \
87 ? ++read_in \
88 : (size_t) (inchar_errno = errno)), c))
90 # define MEMCPY(d, s, n) __wmemcpy (d, s, n)
91 # define ISSPACE(Ch) iswspace (Ch)
92 # define ISDIGIT(Ch) iswdigit (Ch)
93 # define ISXDIGIT(Ch) iswxdigit (Ch)
94 # define TOLOWER(Ch) towlower (Ch)
95 # define ORIENT if (_IO_fwide (s, 1) != 1) return WEOF
96 # define __strtoll_internal __wcstoll_internal
97 # define __strtoull_internal __wcstoull_internal
98 # define __strtol_internal __wcstol_internal
99 # define __strtoul_internal __wcstoul_internal
100 # define __strtold_internal __wcstold_internal
101 # define __strtod_internal __wcstod_internal
102 # define __strtof_internal __wcstof_internal
104 # define L_(Str) L##Str
105 # define CHAR_T wchar_t
106 # define UCHAR_T unsigned int
107 # define WINT_T wint_t
108 # undef EOF
109 # define EOF WEOF
110 #else
111 # define ungetc(c, s) ((void) ((int) c == EOF \
112 || (--read_in, \
113 _IO_sputbackc (s, (unsigned char) c))))
114 # define ungetc_not_eof(c, s) ((void) (--read_in, \
115 _IO_sputbackc (s, (unsigned char) c)))
116 # define inchar() (c == EOF ? ((errno = inchar_errno), EOF) \
117 : ((c = _IO_getc_unlocked (s)), \
118 (void) (c != EOF \
119 ? ++read_in \
120 : (size_t) (inchar_errno = errno)), c))
121 # define MEMCPY(d, s, n) memcpy (d, s, n)
122 # define ISSPACE(Ch) __isspace_l (Ch, loc)
123 # define ISDIGIT(Ch) __isdigit_l (Ch, loc)
124 # define ISXDIGIT(Ch) __isxdigit_l (Ch, loc)
125 # define TOLOWER(Ch) __tolower_l ((unsigned char) (Ch), loc)
126 # define ORIENT if (_IO_vtable_offset (s) == 0 \
127 && _IO_fwide (s, -1) != -1) \
128 return EOF
130 # define L_(Str) Str
131 # define CHAR_T char
132 # define UCHAR_T unsigned char
133 # define WINT_T int
134 #endif
136 #define encode_error() do { \
137 errval = 4; \
138 __set_errno (EILSEQ); \
139 goto errout; \
140 } while (0)
141 #define conv_error() do { \
142 errval = 2; \
143 goto errout; \
144 } while (0)
145 #define input_error() do { \
146 errval = 1; \
147 if (done == 0) done = EOF; \
148 goto errout; \
149 } while (0)
150 #define add_ptr_to_free(ptr) \
151 do \
153 if (ptrs_to_free == NULL \
154 || ptrs_to_free->count == (sizeof (ptrs_to_free->ptrs) \
155 / sizeof (ptrs_to_free->ptrs[0]))) \
157 struct ptrs_to_free *new_ptrs = alloca (sizeof (*ptrs_to_free)); \
158 new_ptrs->count = 0; \
159 new_ptrs->next = ptrs_to_free; \
160 ptrs_to_free = new_ptrs; \
162 ptrs_to_free->ptrs[ptrs_to_free->count++] = (ptr); \
164 while (0)
165 #define ARGCHECK(s, format) \
166 do \
168 /* Check file argument for consistence. */ \
169 CHECK_FILE (s, EOF); \
170 if (s->_flags & _IO_NO_READS) \
172 __set_errno (EBADF); \
173 return EOF; \
175 else if (format == NULL) \
177 MAYBE_SET_EINVAL; \
178 return EOF; \
180 } while (0)
181 #define LOCK_STREAM(S) \
182 __libc_cleanup_region_start (1, (void (*) (void *)) &_IO_funlockfile, (S)); \
183 _IO_flockfile (S)
184 #define UNLOCK_STREAM(S) \
185 _IO_funlockfile (S); \
186 __libc_cleanup_region_end (0)
188 struct ptrs_to_free
190 size_t count;
191 struct ptrs_to_free *next;
192 char **ptrs[32];
195 /* Read formatted input from S according to the format string
196 FORMAT, using the argument list in ARG.
197 Return the number of assignments made, or -1 for an input error. */
198 #ifdef COMPILE_WSCANF
200 _IO_vfwscanf (_IO_FILE *s, const wchar_t *format, _IO_va_list argptr,
201 int *errp)
202 #else
204 _IO_vfscanf_internal (_IO_FILE *s, const char *format, _IO_va_list argptr,
205 int *errp)
206 #endif
208 va_list arg;
209 const CHAR_T *f = format;
210 UCHAR_T fc; /* Current character of the format. */
211 WINT_T done = 0; /* Assignments done. */
212 size_t read_in = 0; /* Chars read in. */
213 WINT_T c = 0; /* Last char read. */
214 int width; /* Maximum field width. */
215 int flags; /* Modifiers for current format element. */
216 int errval = 0;
217 #ifndef COMPILE_WSCANF
218 __locale_t loc = _NL_CURRENT_LOCALE;
219 struct __locale_data *const curctype = loc->__locales[LC_CTYPE];
220 #endif
222 /* Errno of last failed inchar call. */
223 int inchar_errno = 0;
224 /* Status for reading F-P nums. */
225 char got_digit, got_dot, got_e, negative;
226 /* If a [...] is a [^...]. */
227 CHAR_T not_in;
228 #define exp_char not_in
229 /* Base for integral numbers. */
230 int base;
231 /* Decimal point character. */
232 #ifdef COMPILE_WSCANF
233 wint_t decimal;
234 #else
235 const char *decimal;
236 #endif
237 /* The thousands character of the current locale. */
238 #ifdef COMPILE_WSCANF
239 wint_t thousands;
240 #else
241 const char *thousands;
242 #endif
243 struct ptrs_to_free *ptrs_to_free = NULL;
244 /* State for the conversions. */
245 mbstate_t state;
246 /* Integral holding variables. */
247 union
249 long long int q;
250 unsigned long long int uq;
251 long int l;
252 unsigned long int ul;
253 } num;
254 /* Character-buffer pointer. */
255 char *str = NULL;
256 wchar_t *wstr = NULL;
257 char **strptr = NULL;
258 ssize_t strsize = 0;
259 /* We must not react on white spaces immediately because they can
260 possibly be matched even if in the input stream no character is
261 available anymore. */
262 int skip_space = 0;
263 /* Workspace. */
264 CHAR_T *tw; /* Temporary pointer. */
265 CHAR_T *wp = NULL; /* Workspace. */
266 size_t wpmax = 0; /* Maximal size of workspace. */
267 size_t wpsize; /* Currently used bytes in workspace. */
268 bool use_malloc = false;
269 #define ADDW(Ch) \
270 do \
272 if (__builtin_expect (wpsize == wpmax, 0)) \
274 CHAR_T *old = wp; \
275 size_t newsize = (UCHAR_MAX + 1 > 2 * wpmax \
276 ? UCHAR_MAX + 1 : 2 * wpmax); \
277 if (use_malloc || !__libc_use_alloca (newsize)) \
279 wp = realloc (use_malloc ? wp : NULL, newsize); \
280 if (wp == NULL) \
282 if (use_malloc) \
283 free (old); \
284 done = EOF; \
285 goto errout; \
287 if (! use_malloc) \
288 MEMCPY (wp, old, wpsize); \
289 wpmax = newsize; \
290 use_malloc = true; \
292 else \
294 size_t s = wpmax * sizeof (CHAR_T); \
295 wp = (CHAR_T *) extend_alloca (wp, s, \
296 newsize * sizeof (CHAR_T)); \
297 wpmax = s / sizeof (CHAR_T); \
298 if (old != NULL) \
299 MEMCPY (wp, old, wpsize); \
302 wp[wpsize++] = (Ch); \
304 while (0)
306 #ifdef __va_copy
307 __va_copy (arg, argptr);
308 #else
309 arg = (va_list) argptr;
310 #endif
312 #ifdef ORIENT
313 ORIENT;
314 #endif
316 ARGCHECK (s, format);
319 #ifndef COMPILE_WSCANF
320 struct __locale_data *const curnumeric = loc->__locales[LC_NUMERIC];
321 #endif
323 /* Figure out the decimal point character. */
324 #ifdef COMPILE_WSCANF
325 decimal = _NL_CURRENT_WORD (LC_NUMERIC, _NL_NUMERIC_DECIMAL_POINT_WC);
326 #else
327 decimal = curnumeric->values[_NL_ITEM_INDEX (DECIMAL_POINT)].string;
328 #endif
329 /* Figure out the thousands separator character. */
330 #ifdef COMPILE_WSCANF
331 thousands = _NL_CURRENT_WORD (LC_NUMERIC, _NL_NUMERIC_THOUSANDS_SEP_WC);
332 #else
333 thousands = curnumeric->values[_NL_ITEM_INDEX (THOUSANDS_SEP)].string;
334 if (*thousands == '\0')
335 thousands = NULL;
336 #endif
339 /* Lock the stream. */
340 LOCK_STREAM (s);
343 #ifndef COMPILE_WSCANF
344 /* From now on we use `state' to convert the format string. */
345 memset (&state, '\0', sizeof (state));
346 #endif
348 /* Run through the format string. */
349 while (*f != '\0')
351 unsigned int argpos;
352 /* Extract the next argument, which is of type TYPE.
353 For a %N$... spec, this is the Nth argument from the beginning;
354 otherwise it is the next argument after the state now in ARG. */
355 #ifdef __va_copy
356 # define ARG(type) (argpos == 0 ? va_arg (arg, type) : \
357 ({ unsigned int pos = argpos; \
358 va_list arg; \
359 __va_copy (arg, argptr); \
360 while (--pos > 0) \
361 (void) va_arg (arg, void *); \
362 va_arg (arg, type); \
364 #else
365 # if 0
366 /* XXX Possible optimization. */
367 # define ARG(type) (argpos == 0 ? va_arg (arg, type) : \
368 ({ va_list arg = (va_list) argptr; \
369 arg = (va_list) ((char *) arg \
370 + (argpos - 1) \
371 * __va_rounded_size (void *)); \
372 va_arg (arg, type); \
374 # else
375 # define ARG(type) (argpos == 0 ? va_arg (arg, type) : \
376 ({ unsigned int pos = argpos; \
377 va_list arg = (va_list) argptr; \
378 while (--pos > 0) \
379 (void) va_arg (arg, void *); \
380 va_arg (arg, type); \
382 # endif
383 #endif
385 #ifndef COMPILE_WSCANF
386 if (!isascii ((unsigned char) *f))
388 /* Non-ASCII, may be a multibyte. */
389 int len = __mbrlen (f, strlen (f), &state);
390 if (len > 0)
394 c = inchar ();
395 if (__builtin_expect (c == EOF, 0))
396 input_error ();
397 else if (c != (unsigned char) *f++)
399 ungetc_not_eof (c, s);
400 conv_error ();
403 while (--len > 0);
404 continue;
407 #endif
409 fc = *f++;
410 if (fc != '%')
412 /* Remember to skip spaces. */
413 if (ISSPACE (fc))
415 skip_space = 1;
416 continue;
419 /* Read a character. */
420 c = inchar ();
422 /* Characters other than format specs must just match. */
423 if (__builtin_expect (c == EOF, 0))
424 input_error ();
426 /* We saw white space char as the last character in the format
427 string. Now it's time to skip all leading white space. */
428 if (skip_space)
430 while (ISSPACE (c))
431 if (__builtin_expect (inchar () == EOF, 0))
432 input_error ();
433 skip_space = 0;
436 if (__builtin_expect (c != fc, 0))
438 ungetc (c, s);
439 conv_error ();
442 continue;
445 /* This is the start of the conversion string. */
446 flags = 0;
448 /* Initialize state of modifiers. */
449 argpos = 0;
451 /* Prepare temporary buffer. */
452 wpsize = 0;
454 /* Check for a positional parameter specification. */
455 if (ISDIGIT ((UCHAR_T) *f))
457 argpos = (UCHAR_T) *f++ - L_('0');
458 while (ISDIGIT ((UCHAR_T) *f))
459 argpos = argpos * 10 + ((UCHAR_T) *f++ - L_('0'));
460 if (*f == L_('$'))
461 ++f;
462 else
464 /* Oops; that was actually the field width. */
465 width = argpos;
466 argpos = 0;
467 goto got_width;
471 /* Check for the assignment-suppressing, the number grouping flag,
472 and the signal to use the locale's digit representation. */
473 while (*f == L_('*') || *f == L_('\'') || *f == L_('I'))
474 switch (*f++)
476 case L_('*'):
477 flags |= SUPPRESS;
478 break;
479 case L_('\''):
480 #ifdef COMPILE_WSCANF
481 if (thousands != L'\0')
482 #else
483 if (thousands != NULL)
484 #endif
485 flags |= GROUP;
486 break;
487 case L_('I'):
488 flags |= I18N;
489 break;
492 /* Find the maximum field width. */
493 width = 0;
494 while (ISDIGIT ((UCHAR_T) *f))
496 width *= 10;
497 width += (UCHAR_T) *f++ - L_('0');
499 got_width:
500 if (width == 0)
501 width = -1;
503 /* Check for type modifiers. */
504 switch (*f++)
506 case L_('h'):
507 /* ints are short ints or chars. */
508 if (*f == L_('h'))
510 ++f;
511 flags |= CHAR;
513 else
514 flags |= SHORT;
515 break;
516 case L_('l'):
517 if (*f == L_('l'))
519 /* A double `l' is equivalent to an `L'. */
520 ++f;
521 flags |= LONGDBL | LONG;
523 else
524 /* ints are long ints. */
525 flags |= LONG;
526 break;
527 case L_('q'):
528 case L_('L'):
529 /* doubles are long doubles, and ints are long long ints. */
530 flags |= LONGDBL | LONG;
531 break;
532 case L_('a'):
533 /* The `a' is used as a flag only if followed by `s', `S' or
534 `['. */
535 if (*f != L_('s') && *f != L_('S') && *f != L_('['))
537 --f;
538 break;
540 /* In __isoc99_*scanf %as, %aS and %a[ extension is not
541 supported at all. */
542 if (s->_flags2 & _IO_FLAGS2_SCANF_STD)
544 --f;
545 break;
547 /* String conversions (%s, %[) take a `char **'
548 arg and fill it in with a malloc'd pointer. */
549 flags |= GNU_MALLOC;
550 break;
551 case L_('m'):
552 flags |= POSIX_MALLOC;
553 if (*f == L_('l'))
555 ++f;
556 flags |= LONG;
558 break;
559 case L_('z'):
560 if (need_longlong && sizeof (size_t) > sizeof (unsigned long int))
561 flags |= LONGDBL;
562 else if (sizeof (size_t) > sizeof (unsigned int))
563 flags |= LONG;
564 break;
565 case L_('j'):
566 if (need_longlong && sizeof (uintmax_t) > sizeof (unsigned long int))
567 flags |= LONGDBL;
568 else if (sizeof (uintmax_t) > sizeof (unsigned int))
569 flags |= LONG;
570 break;
571 case L_('t'):
572 if (need_longlong && sizeof (ptrdiff_t) > sizeof (long int))
573 flags |= LONGDBL;
574 else if (sizeof (ptrdiff_t) > sizeof (int))
575 flags |= LONG;
576 break;
577 default:
578 /* Not a recognized modifier. Backup. */
579 --f;
580 break;
583 /* End of the format string? */
584 if (__builtin_expect (*f == L_('\0'), 0))
585 conv_error ();
587 /* Find the conversion specifier. */
588 fc = *f++;
589 if (skip_space || (fc != L_('[') && fc != L_('c')
590 && fc != L_('C') && fc != L_('n')))
592 /* Eat whitespace. */
593 int save_errno = errno;
594 __set_errno (0);
596 /* We add the additional test for EOF here since otherwise
597 inchar will restore the old errno value which might be
598 EINTR but does not indicate an interrupt since nothing
599 was read at this time. */
600 if (__builtin_expect ((c == EOF || inchar () == EOF)
601 && errno == EINTR, 0))
602 input_error ();
603 while (ISSPACE (c));
604 __set_errno (save_errno);
605 ungetc (c, s);
606 skip_space = 0;
609 switch (fc)
611 case L_('%'): /* Must match a literal '%'. */
612 c = inchar ();
613 if (__builtin_expect (c == EOF, 0))
614 input_error ();
615 if (__builtin_expect (c != fc, 0))
617 ungetc_not_eof (c, s);
618 conv_error ();
620 break;
622 case L_('n'): /* Answer number of assignments done. */
623 /* Corrigendum 1 to ISO C 1990 describes the allowed flags
624 with the 'n' conversion specifier. */
625 if (!(flags & SUPPRESS))
627 /* Don't count the read-ahead. */
628 if (need_longlong && (flags & LONGDBL))
629 *ARG (long long int *) = read_in;
630 else if (need_long && (flags & LONG))
631 *ARG (long int *) = read_in;
632 else if (flags & SHORT)
633 *ARG (short int *) = read_in;
634 else if (!(flags & CHAR))
635 *ARG (int *) = read_in;
636 else
637 *ARG (char *) = read_in;
639 #ifdef NO_BUG_IN_ISO_C_CORRIGENDUM_1
640 /* We have a severe problem here. The ISO C standard
641 contradicts itself in explaining the effect of the %n
642 format in `scanf'. While in ISO C:1990 and the ISO C
643 Amendement 1:1995 the result is described as
645 Execution of a %n directive does not effect the
646 assignment count returned at the completion of
647 execution of the f(w)scanf function.
649 in ISO C Corrigendum 1:1994 the following was added:
651 Subclause 7.9.6.2
652 Add the following fourth example:
654 #include <stdio.h>
655 int d1, d2, n1, n2, i;
656 i = sscanf("123", "%d%n%n%d", &d1, &n1, &n2, &d2);
657 the value 123 is assigned to d1 and the value3 to n1.
658 Because %n can never get an input failure the value
659 of 3 is also assigned to n2. The value of d2 is not
660 affected. The value 3 is assigned to i.
662 We go for now with the historically correct code from ISO C,
663 i.e., we don't count the %n assignments. When it ever
664 should proof to be wrong just remove the #ifdef above. */
665 ++done;
666 #endif
668 break;
670 case L_('c'): /* Match characters. */
671 if ((flags & LONG) == 0)
673 if (width == -1)
674 width = 1;
676 #define STRING_ARG(Str, Type, Width) \
677 do if (!(flags & SUPPRESS)) \
679 if (flags & MALLOC) \
681 /* The string is to be stored in a malloc'd buffer. */ \
682 /* For %mS using char ** is actually wrong, but \
683 shouldn't make a difference on any arch glibc \
684 supports and would unnecessarily complicate \
685 things. */ \
686 strptr = ARG (char **); \
687 if (strptr == NULL) \
688 conv_error (); \
689 /* Allocate an initial buffer. */ \
690 strsize = Width; \
691 *strptr = (char *) malloc (strsize * sizeof (Type)); \
692 Str = (Type *) *strptr; \
693 if (Str != NULL) \
694 add_ptr_to_free (strptr); \
695 else if (flags & POSIX_MALLOC) \
697 done = EOF; \
698 goto errout; \
701 else \
702 Str = ARG (Type *); \
703 if (Str == NULL) \
704 conv_error (); \
705 } while (0)
706 #ifdef COMPILE_WSCANF
707 STRING_ARG (str, char, 100);
708 #else
709 STRING_ARG (str, char, (width > 1024 ? 1024 : width));
710 #endif
712 c = inchar ();
713 if (__builtin_expect (c == EOF, 0))
714 input_error ();
716 #ifdef COMPILE_WSCANF
717 /* We have to convert the wide character(s) into multibyte
718 characters and store the result. */
719 memset (&state, '\0', sizeof (state));
723 size_t n;
725 if (!(flags & SUPPRESS) && (flags & POSIX_MALLOC)
726 && str + MB_CUR_MAX >= *strptr + strsize)
728 /* We have to enlarge the buffer if the `m' flag
729 was given. */
730 size_t strleng = str - *strptr;
731 char *newstr;
733 newstr = (char *) realloc (*strptr, strsize * 2);
734 if (newstr == NULL)
736 /* Can't allocate that much. Last-ditch effort. */
737 newstr = (char *) realloc (*strptr,
738 strleng + MB_CUR_MAX);
739 if (newstr == NULL)
741 /* c can't have `a' flag, only `m'. */
742 done = EOF;
743 goto errout;
745 else
747 *strptr = newstr;
748 str = newstr + strleng;
749 strsize = strleng + MB_CUR_MAX;
752 else
754 *strptr = newstr;
755 str = newstr + strleng;
756 strsize *= 2;
760 n = __wcrtomb (!(flags & SUPPRESS) ? str : NULL, c, &state);
761 if (__builtin_expect (n == (size_t) -1, 0))
762 /* No valid wide character. */
763 input_error ();
765 /* Increment the output pointer. Even if we don't
766 write anything. */
767 str += n;
769 while (--width > 0 && inchar () != EOF);
770 #else
771 if (!(flags & SUPPRESS))
775 if ((flags & MALLOC)
776 && (char *) str == *strptr + strsize)
778 /* Enlarge the buffer. */
779 size_t newsize
780 = strsize
781 + (strsize >= width ? width - 1 : strsize);
783 str = (char *) realloc (*strptr, newsize);
784 if (str == NULL)
786 /* Can't allocate that much. Last-ditch
787 effort. */
788 str = (char *) realloc (*strptr, strsize + 1);
789 if (str == NULL)
791 /* c can't have `a' flag, only `m'. */
792 done = EOF;
793 goto errout;
795 else
797 *strptr = (char *) str;
798 str += strsize;
799 ++strsize;
802 else
804 *strptr = (char *) str;
805 str += strsize;
806 strsize = newsize;
809 *str++ = c;
811 while (--width > 0 && inchar () != EOF);
813 else
814 while (--width > 0 && inchar () != EOF);
815 #endif
817 if (!(flags & SUPPRESS))
819 if ((flags & MALLOC) && str - *strptr != strsize)
821 char *cp = (char *) realloc (*strptr, str - *strptr);
822 if (cp != NULL)
823 *strptr = cp;
825 strptr = NULL;
826 ++done;
829 break;
831 /* FALLTHROUGH */
832 case L_('C'):
833 if (width == -1)
834 width = 1;
836 STRING_ARG (wstr, wchar_t, (width > 1024 ? 1024 : width));
838 c = inchar ();
839 if (__builtin_expect (c == EOF, 0))
840 input_error ();
842 #ifdef COMPILE_WSCANF
843 /* Just store the incoming wide characters. */
844 if (!(flags & SUPPRESS))
848 if ((flags & MALLOC)
849 && wstr == (wchar_t *) *strptr + strsize)
851 size_t newsize
852 = strsize + (strsize > width ? width - 1 : strsize);
853 /* Enlarge the buffer. */
854 wstr = (wchar_t *) realloc (*strptr,
855 newsize * sizeof (wchar_t));
856 if (wstr == NULL)
858 /* Can't allocate that much. Last-ditch effort. */
859 wstr = (wchar_t *) realloc (*strptr,
860 (strsize + 1)
861 * sizeof (wchar_t));
862 if (wstr == NULL)
864 /* C or lc can't have `a' flag, only `m'
865 flag. */
866 done = EOF;
867 goto errout;
869 else
871 *strptr = (char *) wstr;
872 wstr += strsize;
873 ++strsize;
876 else
878 *strptr = (char *) wstr;
879 wstr += strsize;
880 strsize = newsize;
883 *wstr++ = c;
885 while (--width > 0 && inchar () != EOF);
887 else
888 while (--width > 0 && inchar () != EOF);
889 #else
891 /* We have to convert the multibyte input sequence to wide
892 characters. */
893 char buf[1];
894 mbstate_t cstate;
896 memset (&cstate, '\0', sizeof (cstate));
900 /* This is what we present the mbrtowc function first. */
901 buf[0] = c;
903 if (!(flags & SUPPRESS) && (flags & MALLOC)
904 && wstr == (wchar_t *) *strptr + strsize)
906 size_t newsize
907 = strsize + (strsize > width ? width - 1 : strsize);
908 /* Enlarge the buffer. */
909 wstr = (wchar_t *) realloc (*strptr,
910 newsize * sizeof (wchar_t));
911 if (wstr == NULL)
913 /* Can't allocate that much. Last-ditch effort. */
914 wstr = (wchar_t *) realloc (*strptr,
915 ((strsize + 1)
916 * sizeof (wchar_t)));
917 if (wstr == NULL)
919 /* C or lc can't have `a' flag, only `m' flag. */
920 done = EOF;
921 goto errout;
923 else
925 *strptr = (char *) wstr;
926 wstr += strsize;
927 ++strsize;
930 else
932 *strptr = (char *) wstr;
933 wstr += strsize;
934 strsize = newsize;
938 while (1)
940 size_t n;
942 n = __mbrtowc (!(flags & SUPPRESS) ? wstr : NULL,
943 buf, 1, &cstate);
945 if (n == (size_t) -2)
947 /* Possibly correct character, just not enough
948 input. */
949 if (__builtin_expect (inchar () == EOF, 0))
950 encode_error ();
952 buf[0] = c;
953 continue;
956 if (__builtin_expect (n != 1, 0))
957 encode_error ();
959 /* We have a match. */
960 break;
963 /* Advance the result pointer. */
964 ++wstr;
966 while (--width > 0 && inchar () != EOF);
968 #endif
970 if (!(flags & SUPPRESS))
972 if ((flags & MALLOC) && wstr - (wchar_t *) *strptr != strsize)
974 wchar_t *cp = (wchar_t *) realloc (*strptr,
975 ((wstr
976 - (wchar_t *) *strptr)
977 * sizeof (wchar_t)));
978 if (cp != NULL)
979 *strptr = (char *) cp;
981 strptr = NULL;
983 ++done;
986 break;
988 case L_('s'): /* Read a string. */
989 if (!(flags & LONG))
991 STRING_ARG (str, char, 100);
993 c = inchar ();
994 if (__builtin_expect (c == EOF, 0))
995 input_error ();
997 #ifdef COMPILE_WSCANF
998 memset (&state, '\0', sizeof (state));
999 #endif
1003 if (ISSPACE (c))
1005 ungetc_not_eof (c, s);
1006 break;
1009 #ifdef COMPILE_WSCANF
1010 /* This is quite complicated. We have to convert the
1011 wide characters into multibyte characters and then
1012 store them. */
1014 size_t n;
1016 if (!(flags & SUPPRESS) && (flags & MALLOC)
1017 && str + MB_CUR_MAX >= *strptr + strsize)
1019 /* We have to enlarge the buffer if the `a' or `m'
1020 flag was given. */
1021 size_t strleng = str - *strptr;
1022 char *newstr;
1024 newstr = (char *) realloc (*strptr, strsize * 2);
1025 if (newstr == NULL)
1027 /* Can't allocate that much. Last-ditch
1028 effort. */
1029 newstr = (char *) realloc (*strptr,
1030 strleng + MB_CUR_MAX);
1031 if (newstr == NULL)
1033 if (flags & POSIX_MALLOC)
1035 done = EOF;
1036 goto errout;
1038 /* We lose. Oh well. Terminate the
1039 string and stop converting,
1040 so at least we don't skip any input. */
1041 ((char *) (*strptr))[strleng] = '\0';
1042 strptr = NULL;
1043 ++done;
1044 conv_error ();
1046 else
1048 *strptr = newstr;
1049 str = newstr + strleng;
1050 strsize = strleng + MB_CUR_MAX;
1053 else
1055 *strptr = newstr;
1056 str = newstr + strleng;
1057 strsize *= 2;
1061 n = __wcrtomb (!(flags & SUPPRESS) ? str : NULL, c,
1062 &state);
1063 if (__builtin_expect (n == (size_t) -1, 0))
1064 encode_error ();
1066 assert (n <= MB_CUR_MAX);
1067 str += n;
1069 #else
1070 /* This is easy. */
1071 if (!(flags & SUPPRESS))
1073 *str++ = c;
1074 if ((flags & MALLOC)
1075 && (char *) str == *strptr + strsize)
1077 /* Enlarge the buffer. */
1078 str = (char *) realloc (*strptr, 2 * strsize);
1079 if (str == NULL)
1081 /* Can't allocate that much. Last-ditch
1082 effort. */
1083 str = (char *) realloc (*strptr, strsize + 1);
1084 if (str == NULL)
1086 if (flags & POSIX_MALLOC)
1088 done = EOF;
1089 goto errout;
1091 /* We lose. Oh well. Terminate the
1092 string and stop converting,
1093 so at least we don't skip any input. */
1094 ((char *) (*strptr))[strsize - 1] = '\0';
1095 strptr = NULL;
1096 ++done;
1097 conv_error ();
1099 else
1101 *strptr = (char *) str;
1102 str += strsize;
1103 ++strsize;
1106 else
1108 *strptr = (char *) str;
1109 str += strsize;
1110 strsize *= 2;
1114 #endif
1116 while ((width <= 0 || --width > 0) && inchar () != EOF);
1118 if (!(flags & SUPPRESS))
1120 #ifdef COMPILE_WSCANF
1121 /* We have to emit the code to get into the initial
1122 state. */
1123 char buf[MB_LEN_MAX];
1124 size_t n = __wcrtomb (buf, L'\0', &state);
1125 if (n > 0 && (flags & MALLOC)
1126 && str + n >= *strptr + strsize)
1128 /* Enlarge the buffer. */
1129 size_t strleng = str - *strptr;
1130 char *newstr;
1132 newstr = (char *) realloc (*strptr, strleng + n + 1);
1133 if (newstr == NULL)
1135 if (flags & POSIX_MALLOC)
1137 done = EOF;
1138 goto errout;
1140 /* We lose. Oh well. Terminate the string
1141 and stop converting, so at least we don't
1142 skip any input. */
1143 ((char *) (*strptr))[strleng] = '\0';
1144 strptr = NULL;
1145 ++done;
1146 conv_error ();
1148 else
1150 *strptr = newstr;
1151 str = newstr + strleng;
1152 strsize = strleng + n + 1;
1156 str = __mempcpy (str, buf, n);
1157 #endif
1158 *str++ = '\0';
1160 if ((flags & MALLOC) && str - *strptr != strsize)
1162 char *cp = (char *) realloc (*strptr, str - *strptr);
1163 if (cp != NULL)
1164 *strptr = cp;
1166 strptr = NULL;
1168 ++done;
1170 break;
1172 /* FALLTHROUGH */
1174 case L_('S'):
1176 #ifndef COMPILE_WSCANF
1177 mbstate_t cstate;
1178 #endif
1180 /* Wide character string. */
1181 STRING_ARG (wstr, wchar_t, 100);
1183 c = inchar ();
1184 if (__builtin_expect (c == EOF, 0))
1185 input_error ();
1187 #ifndef COMPILE_WSCANF
1188 memset (&cstate, '\0', sizeof (cstate));
1189 #endif
1193 if (ISSPACE (c))
1195 ungetc_not_eof (c, s);
1196 break;
1199 #ifdef COMPILE_WSCANF
1200 /* This is easy. */
1201 if (!(flags & SUPPRESS))
1203 *wstr++ = c;
1204 if ((flags & MALLOC)
1205 && wstr == (wchar_t *) *strptr + strsize)
1207 /* Enlarge the buffer. */
1208 wstr = (wchar_t *) realloc (*strptr,
1209 (2 * strsize)
1210 * sizeof (wchar_t));
1211 if (wstr == NULL)
1213 /* Can't allocate that much. Last-ditch
1214 effort. */
1215 wstr = (wchar_t *) realloc (*strptr,
1216 (strsize + 1)
1217 * sizeof (wchar_t));
1218 if (wstr == NULL)
1220 if (flags & POSIX_MALLOC)
1222 done = EOF;
1223 goto errout;
1225 /* We lose. Oh well. Terminate the string
1226 and stop converting, so at least we don't
1227 skip any input. */
1228 ((wchar_t *) (*strptr))[strsize - 1] = L'\0';
1229 strptr = NULL;
1230 ++done;
1231 conv_error ();
1233 else
1235 *strptr = (char *) wstr;
1236 wstr += strsize;
1237 ++strsize;
1240 else
1242 *strptr = (char *) wstr;
1243 wstr += strsize;
1244 strsize *= 2;
1248 #else
1250 char buf[1];
1252 buf[0] = c;
1254 while (1)
1256 size_t n;
1258 n = __mbrtowc (!(flags & SUPPRESS) ? wstr : NULL,
1259 buf, 1, &cstate);
1261 if (n == (size_t) -2)
1263 /* Possibly correct character, just not enough
1264 input. */
1265 if (__builtin_expect (inchar () == EOF, 0))
1266 encode_error ();
1268 buf[0] = c;
1269 continue;
1272 if (__builtin_expect (n != 1, 0))
1273 encode_error ();
1275 /* We have a match. */
1276 ++wstr;
1277 break;
1280 if (!(flags & SUPPRESS) && (flags & MALLOC)
1281 && wstr == (wchar_t *) *strptr + strsize)
1283 /* Enlarge the buffer. */
1284 wstr = (wchar_t *) realloc (*strptr,
1285 (2 * strsize
1286 * sizeof (wchar_t)));
1287 if (wstr == NULL)
1289 /* Can't allocate that much. Last-ditch effort. */
1290 wstr = (wchar_t *) realloc (*strptr,
1291 ((strsize + 1)
1292 * sizeof (wchar_t)));
1293 if (wstr == NULL)
1295 if (flags & POSIX_MALLOC)
1297 done = EOF;
1298 goto errout;
1300 /* We lose. Oh well. Terminate the
1301 string and stop converting, so at
1302 least we don't skip any input. */
1303 ((wchar_t *) (*strptr))[strsize - 1] = L'\0';
1304 strptr = NULL;
1305 ++done;
1306 conv_error ();
1308 else
1310 *strptr = (char *) wstr;
1311 wstr += strsize;
1312 ++strsize;
1315 else
1317 *strptr = (char *) wstr;
1318 wstr += strsize;
1319 strsize *= 2;
1323 #endif
1325 while ((width <= 0 || --width > 0) && inchar () != EOF);
1327 if (!(flags & SUPPRESS))
1329 *wstr++ = L'\0';
1331 if ((flags & MALLOC) && wstr - (wchar_t *) *strptr != strsize)
1333 wchar_t *cp = (wchar_t *) realloc (*strptr,
1334 ((wstr
1335 - (wchar_t *) *strptr)
1336 * sizeof(wchar_t)));
1337 if (cp != NULL)
1338 *strptr = (char *) cp;
1340 strptr = NULL;
1342 ++done;
1345 break;
1347 case L_('x'): /* Hexadecimal integer. */
1348 case L_('X'): /* Ditto. */
1349 base = 16;
1350 goto number;
1352 case L_('o'): /* Octal integer. */
1353 base = 8;
1354 goto number;
1356 case L_('u'): /* Unsigned decimal integer. */
1357 base = 10;
1358 goto number;
1360 case L_('d'): /* Signed decimal integer. */
1361 base = 10;
1362 flags |= NUMBER_SIGNED;
1363 goto number;
1365 case L_('i'): /* Generic number. */
1366 base = 0;
1367 flags |= NUMBER_SIGNED;
1369 number:
1370 c = inchar ();
1371 if (__builtin_expect (c == EOF, 0))
1372 input_error ();
1374 /* Check for a sign. */
1375 if (c == L_('-') || c == L_('+'))
1377 ADDW (c);
1378 if (width > 0)
1379 --width;
1380 c = inchar ();
1383 /* Look for a leading indication of base. */
1384 if (width != 0 && c == L_('0'))
1386 if (width > 0)
1387 --width;
1389 ADDW (c);
1390 c = inchar ();
1392 if (width != 0 && TOLOWER (c) == L_('x'))
1394 if (base == 0)
1395 base = 16;
1396 if (base == 16)
1398 if (width > 0)
1399 --width;
1400 c = inchar ();
1403 else if (base == 0)
1404 base = 8;
1407 if (base == 0)
1408 base = 10;
1410 if (base == 10 && __builtin_expect ((flags & I18N) != 0, 0))
1412 int from_level;
1413 int to_level;
1414 int level;
1415 #ifdef COMPILE_WSCANF
1416 const wchar_t *wcdigits[10];
1417 const wchar_t *wcdigits_extended[10];
1418 #else
1419 const char *mbdigits[10];
1420 const char *mbdigits_extended[10];
1421 #endif
1422 /* "to_inpunct" is a map from ASCII digits to their
1423 equivalent in locale. This is defined for locales
1424 which use an extra digits set. */
1425 wctrans_t map = __wctrans ("to_inpunct");
1426 int n;
1428 from_level = 0;
1429 #ifdef COMPILE_WSCANF
1430 to_level = _NL_CURRENT_WORD (LC_CTYPE,
1431 _NL_CTYPE_INDIGITS_WC_LEN) - 1;
1432 #else
1433 to_level = (uint32_t) curctype->values[_NL_ITEM_INDEX (_NL_CTYPE_INDIGITS_MB_LEN)].word - 1;
1434 #endif
1436 /* Get the alternative digit forms if there are any. */
1437 if (__builtin_expect (map != NULL, 0))
1439 /* Adding new level for extra digits set in locale file. */
1440 ++to_level;
1442 for (n = 0; n < 10; ++n)
1444 #ifdef COMPILE_WSCANF
1445 wcdigits[n] = (const wchar_t *)
1446 _NL_CURRENT (LC_CTYPE, _NL_CTYPE_INDIGITS0_WC + n);
1448 wchar_t *wc_extended = (wchar_t *)
1449 alloca ((to_level + 2) * sizeof (wchar_t));
1450 __wmemcpy (wc_extended, wcdigits[n], to_level);
1451 wc_extended[to_level] = __towctrans (L'0' + n, map);
1452 wc_extended[to_level + 1] = '\0';
1453 wcdigits_extended[n] = wc_extended;
1454 #else
1455 mbdigits[n]
1456 = curctype->values[_NL_CTYPE_INDIGITS0_MB + n].string;
1458 /* Get the equivalent wide char in map. */
1459 wint_t extra_wcdigit = __towctrans (L'0' + n, map);
1461 /* Convert it to multibyte representation. */
1462 mbstate_t state;
1463 memset (&state, '\0', sizeof (state));
1465 char extra_mbdigit[MB_LEN_MAX];
1466 size_t mblen
1467 = __wcrtomb (extra_mbdigit, extra_wcdigit, &state);
1469 if (mblen == (size_t) -1)
1471 /* Ignore this new level. */
1472 map = NULL;
1473 break;
1476 /* Calculate the length of mbdigits[n]. */
1477 const char *last_char = mbdigits[n];
1478 for (level = 0; level < to_level; ++level)
1479 last_char = strchr (last_char, '\0') + 1;
1481 size_t mbdigits_len = last_char - mbdigits[n];
1483 /* Allocate memory for extended multibyte digit. */
1484 char *mb_extended;
1485 mb_extended = (char *) alloca (mbdigits_len + mblen + 1);
1487 /* And get the mbdigits + extra_digit string. */
1488 *(char *) __mempcpy (__mempcpy (mb_extended, mbdigits[n],
1489 mbdigits_len),
1490 extra_mbdigit, mblen) = '\0';
1491 mbdigits_extended[n] = mb_extended;
1492 #endif
1496 /* Read the number into workspace. */
1497 while (c != EOF && width != 0)
1499 /* In this round we get the pointer to the digit strings
1500 and also perform the first round of comparisons. */
1501 for (n = 0; n < 10; ++n)
1503 /* Get the string for the digits with value N. */
1504 #ifdef COMPILE_WSCANF
1505 if (__builtin_expect (map != NULL, 0))
1506 wcdigits[n] = wcdigits_extended[n];
1507 else
1508 wcdigits[n] = (const wchar_t *)
1509 _NL_CURRENT (LC_CTYPE, _NL_CTYPE_INDIGITS0_WC + n);
1510 wcdigits[n] += from_level;
1512 if (c == (wint_t) *wcdigits[n])
1514 to_level = from_level;
1515 break;
1518 /* Advance the pointer to the next string. */
1519 ++wcdigits[n];
1520 #else
1521 const char *cmpp;
1522 int avail = width > 0 ? width : INT_MAX;
1524 if (__builtin_expect (map != NULL, 0))
1525 mbdigits[n] = mbdigits_extended[n];
1526 else
1527 mbdigits[n]
1528 = curctype->values[_NL_CTYPE_INDIGITS0_MB + n].string;
1530 for (level = 0; level < from_level; level++)
1531 mbdigits[n] = strchr (mbdigits[n], '\0') + 1;
1533 cmpp = mbdigits[n];
1534 while ((unsigned char) *cmpp == c && avail >= 0)
1536 if (*++cmpp == '\0')
1537 break;
1538 else
1540 if (avail == 0 || inchar () == EOF)
1541 break;
1542 --avail;
1546 if (*cmpp == '\0')
1548 if (width > 0)
1549 width = avail;
1550 to_level = from_level;
1551 break;
1554 /* We are pushing all read characters back. */
1555 if (cmpp > mbdigits[n])
1557 ungetc (c, s);
1558 while (--cmpp > mbdigits[n])
1559 ungetc_not_eof ((unsigned char) *cmpp, s);
1560 c = (unsigned char) *cmpp;
1563 /* Advance the pointer to the next string. */
1564 mbdigits[n] = strchr (mbdigits[n], '\0') + 1;
1565 #endif
1568 if (n == 10)
1570 /* Have not yet found the digit. */
1571 for (level = from_level + 1; level <= to_level; ++level)
1573 /* Search all ten digits of this level. */
1574 for (n = 0; n < 10; ++n)
1576 #ifdef COMPILE_WSCANF
1577 if (c == (wint_t) *wcdigits[n])
1578 break;
1580 /* Advance the pointer to the next string. */
1581 ++wcdigits[n];
1582 #else
1583 const char *cmpp;
1584 int avail = width > 0 ? width : INT_MAX;
1586 cmpp = mbdigits[n];
1587 while ((unsigned char) *cmpp == c && avail >= 0)
1589 if (*++cmpp == '\0')
1590 break;
1591 else
1593 if (avail == 0 || inchar () == EOF)
1594 break;
1595 --avail;
1599 if (*cmpp == '\0')
1601 if (width > 0)
1602 width = avail;
1603 break;
1606 /* We are pushing all read characters back. */
1607 if (cmpp > mbdigits[n])
1609 ungetc (c, s);
1610 while (--cmpp > mbdigits[n])
1611 ungetc_not_eof ((unsigned char) *cmpp, s);
1612 c = (unsigned char) *cmpp;
1615 /* Advance the pointer to the next string. */
1616 mbdigits[n] = strchr (mbdigits[n], '\0') + 1;
1617 #endif
1620 if (n < 10)
1622 /* Found it. */
1623 from_level = level;
1624 to_level = level;
1625 break;
1630 if (n < 10)
1631 c = L_('0') + n;
1632 else if (flags & GROUP)
1634 /* Try matching against the thousands separator. */
1635 #ifdef COMPILE_WSCANF
1636 if (c != thousands)
1637 break;
1638 #else
1639 const char *cmpp = thousands;
1640 int avail = width > 0 ? width : INT_MAX;
1642 while ((unsigned char) *cmpp == c && avail >= 0)
1644 ADDW (c);
1645 if (*++cmpp == '\0')
1646 break;
1647 else
1649 if (avail == 0 || inchar () == EOF)
1650 break;
1651 --avail;
1655 if (*cmpp != '\0')
1657 /* We are pushing all read characters back. */
1658 if (cmpp > thousands)
1660 wpsize -= cmpp - thousands;
1661 ungetc (c, s);
1662 while (--cmpp > thousands)
1663 ungetc_not_eof ((unsigned char) *cmpp, s);
1664 c = (unsigned char) *cmpp;
1666 break;
1669 if (width > 0)
1670 width = avail;
1672 /* The last thousands character will be added back by
1673 the ADDW below. */
1674 --wpsize;
1675 #endif
1677 else
1678 break;
1680 ADDW (c);
1681 if (width > 0)
1682 --width;
1684 c = inchar ();
1687 else
1688 /* Read the number into workspace. */
1689 while (c != EOF && width != 0)
1691 if (base == 16)
1693 if (!ISXDIGIT (c))
1694 break;
1696 else if (!ISDIGIT (c) || (int) (c - L_('0')) >= base)
1698 if (base == 10 && (flags & GROUP))
1700 /* Try matching against the thousands separator. */
1701 #ifdef COMPILE_WSCANF
1702 if (c != thousands)
1703 break;
1704 #else
1705 const char *cmpp = thousands;
1706 int avail = width > 0 ? width : INT_MAX;
1708 while ((unsigned char) *cmpp == c && avail >= 0)
1710 ADDW (c);
1711 if (*++cmpp == '\0')
1712 break;
1713 else
1715 if (avail == 0 || inchar () == EOF)
1716 break;
1717 --avail;
1721 if (*cmpp != '\0')
1723 /* We are pushing all read characters back. */
1724 if (cmpp > thousands)
1726 wpsize -= cmpp - thousands;
1727 ungetc (c, s);
1728 while (--cmpp > thousands)
1729 ungetc_not_eof ((unsigned char) *cmpp, s);
1730 c = (unsigned char) *cmpp;
1732 break;
1735 if (width > 0)
1736 width = avail;
1738 /* The last thousands character will be added back by
1739 the ADDW below. */
1740 --wpsize;
1741 #endif
1743 else
1744 break;
1746 ADDW (c);
1747 if (width > 0)
1748 --width;
1750 c = inchar ();
1753 if (wpsize == 0
1754 || (wpsize == 1 && (wp[0] == L_('+') || wp[0] == L_('-'))))
1756 /* There was no number. If we are supposed to read a pointer
1757 we must recognize "(nil)" as well. */
1758 if (__builtin_expect (wpsize == 0
1759 && (flags & READ_POINTER)
1760 && (width < 0 || width >= 0)
1761 && c == '('
1762 && TOLOWER (inchar ()) == L_('n')
1763 && TOLOWER (inchar ()) == L_('i')
1764 && TOLOWER (inchar ()) == L_('l')
1765 && inchar () == L_(')'), 1))
1766 /* We must produce the value of a NULL pointer. A single
1767 '0' digit is enough. */
1768 ADDW (L_('0'));
1769 else
1771 /* The last read character is not part of the number
1772 anymore. */
1773 ungetc (c, s);
1775 conv_error ();
1778 else
1779 /* The just read character is not part of the number anymore. */
1780 ungetc (c, s);
1782 /* Convert the number. */
1783 ADDW (L_('\0'));
1784 if (need_longlong && (flags & LONGDBL))
1786 if (flags & NUMBER_SIGNED)
1787 num.q = __strtoll_internal (wp, &tw, base, flags & GROUP);
1788 else
1789 num.uq = __strtoull_internal (wp, &tw, base, flags & GROUP);
1791 else
1793 if (flags & NUMBER_SIGNED)
1794 num.l = __strtol_internal (wp, &tw, base, flags & GROUP);
1795 else
1796 num.ul = __strtoul_internal (wp, &tw, base, flags & GROUP);
1798 if (__builtin_expect (wp == tw, 0))
1799 conv_error ();
1801 if (!(flags & SUPPRESS))
1803 if (flags & NUMBER_SIGNED)
1805 if (need_longlong && (flags & LONGDBL))
1806 *ARG (LONGLONG int *) = num.q;
1807 else if (need_long && (flags & LONG))
1808 *ARG (long int *) = num.l;
1809 else if (flags & SHORT)
1810 *ARG (short int *) = (short int) num.l;
1811 else if (!(flags & CHAR))
1812 *ARG (int *) = (int) num.l;
1813 else
1814 *ARG (signed char *) = (signed char) num.ul;
1816 else
1818 if (need_longlong && (flags & LONGDBL))
1819 *ARG (unsigned LONGLONG int *) = num.uq;
1820 else if (need_long && (flags & LONG))
1821 *ARG (unsigned long int *) = num.ul;
1822 else if (flags & SHORT)
1823 *ARG (unsigned short int *)
1824 = (unsigned short int) num.ul;
1825 else if (!(flags & CHAR))
1826 *ARG (unsigned int *) = (unsigned int) num.ul;
1827 else
1828 *ARG (unsigned char *) = (unsigned char) num.ul;
1830 ++done;
1832 break;
1834 case L_('e'): /* Floating-point numbers. */
1835 case L_('E'):
1836 case L_('f'):
1837 case L_('F'):
1838 case L_('g'):
1839 case L_('G'):
1840 case L_('a'):
1841 case L_('A'):
1842 c = inchar ();
1843 if (width > 0)
1844 --width;
1845 if (__builtin_expect (c == EOF, 0))
1846 input_error ();
1848 got_digit = got_dot = got_e = 0;
1850 /* Check for a sign. */
1851 if (c == L_('-') || c == L_('+'))
1853 negative = c == L_('-');
1854 if (__builtin_expect (width == 0 || inchar () == EOF, 0))
1855 /* EOF is only an input error before we read any chars. */
1856 conv_error ();
1857 if (width > 0)
1858 --width;
1860 else
1861 negative = 0;
1863 /* Take care for the special arguments "nan" and "inf". */
1864 if (TOLOWER (c) == L_('n'))
1866 /* Maybe "nan". */
1867 ADDW (c);
1868 if (__builtin_expect (width == 0
1869 || inchar () == EOF
1870 || TOLOWER (c) != L_('a'), 0))
1871 conv_error ();
1872 if (width > 0)
1873 --width;
1874 ADDW (c);
1875 if (__builtin_expect (width == 0
1876 || inchar () == EOF
1877 || TOLOWER (c) != L_('n'), 0))
1878 conv_error ();
1879 if (width > 0)
1880 --width;
1881 ADDW (c);
1882 /* It is "nan". */
1883 goto scan_float;
1885 else if (TOLOWER (c) == L_('i'))
1887 /* Maybe "inf" or "infinity". */
1888 ADDW (c);
1889 if (__builtin_expect (width == 0
1890 || inchar () == EOF
1891 || TOLOWER (c) != L_('n'), 0))
1892 conv_error ();
1893 if (width > 0)
1894 --width;
1895 ADDW (c);
1896 if (__builtin_expect (width == 0
1897 || inchar () == EOF
1898 || TOLOWER (c) != L_('f'), 0))
1899 conv_error ();
1900 if (width > 0)
1901 --width;
1902 ADDW (c);
1903 /* It is as least "inf". */
1904 if (width != 0 && inchar () != EOF)
1906 if (TOLOWER (c) == L_('i'))
1908 if (width > 0)
1909 --width;
1910 /* Now we have to read the rest as well. */
1911 ADDW (c);
1912 if (__builtin_expect (width == 0
1913 || inchar () == EOF
1914 || TOLOWER (c) != L_('n'), 0))
1915 conv_error ();
1916 if (width > 0)
1917 --width;
1918 ADDW (c);
1919 if (__builtin_expect (width == 0
1920 || inchar () == EOF
1921 || TOLOWER (c) != L_('i'), 0))
1922 conv_error ();
1923 if (width > 0)
1924 --width;
1925 ADDW (c);
1926 if (__builtin_expect (width == 0
1927 || inchar () == EOF
1928 || TOLOWER (c) != L_('t'), 0))
1929 conv_error ();
1930 if (width > 0)
1931 --width;
1932 ADDW (c);
1933 if (__builtin_expect (width == 0
1934 || inchar () == EOF
1935 || TOLOWER (c) != L_('y'), 0))
1936 conv_error ();
1937 if (width > 0)
1938 --width;
1939 ADDW (c);
1941 else
1942 /* Never mind. */
1943 ungetc (c, s);
1945 goto scan_float;
1948 exp_char = L_('e');
1949 if (width != 0 && c == L_('0'))
1951 ADDW (c);
1952 c = inchar ();
1953 if (width > 0)
1954 --width;
1955 if (width != 0 && TOLOWER (c) == L_('x'))
1957 /* It is a number in hexadecimal format. */
1958 ADDW (c);
1960 flags |= HEXA_FLOAT;
1961 exp_char = L_('p');
1963 /* Grouping is not allowed. */
1964 flags &= ~GROUP;
1965 c = inchar ();
1966 if (width > 0)
1967 --width;
1971 while (1)
1973 if (ISDIGIT (c))
1975 ADDW (c);
1976 got_digit = 1;
1978 else if (!got_e && (flags & HEXA_FLOAT) && ISXDIGIT (c))
1980 ADDW (c);
1981 got_digit = 1;
1983 else if (got_e && wp[wpsize - 1] == exp_char
1984 && (c == L_('-') || c == L_('+')))
1985 ADDW (c);
1986 else if (got_digit && !got_e
1987 && (CHAR_T) TOLOWER (c) == exp_char)
1989 ADDW (exp_char);
1990 got_e = got_dot = 1;
1992 else
1994 #ifdef COMPILE_WSCANF
1995 if (! got_dot && c == decimal)
1997 ADDW (c);
1998 got_dot = 1;
2000 else if ((flags & GROUP) != 0 && ! got_dot && c == thousands)
2001 ADDW (c);
2002 else
2004 /* The last read character is not part of the number
2005 anymore. */
2006 ungetc (c, s);
2007 break;
2009 #else
2010 const char *cmpp = decimal;
2011 int avail = width > 0 ? width : INT_MAX;
2013 if (! got_dot)
2015 while ((unsigned char) *cmpp == c && avail >= 0)
2016 if (*++cmpp == '\0')
2017 break;
2018 else
2020 if (avail == 0 || inchar () == EOF)
2021 break;
2022 --avail;
2026 if (*cmpp == '\0')
2028 /* Add all the characters. */
2029 for (cmpp = decimal; *cmpp != '\0'; ++cmpp)
2030 ADDW ((unsigned char) *cmpp);
2031 if (width > 0)
2032 width = avail;
2033 got_dot = 1;
2035 else
2037 /* Figure out whether it is a thousands separator.
2038 There is one problem: we possibly read more than
2039 one character. We cannot push them back but since
2040 we know that parts of the `decimal' string matched,
2041 we can compare against it. */
2042 const char *cmp2p = thousands;
2044 if ((flags & GROUP) != 0 && ! got_dot)
2046 while (cmp2p - thousands < cmpp - decimal
2047 && *cmp2p == decimal[cmp2p - thousands])
2048 ++cmp2p;
2049 if (cmp2p - thousands == cmpp - decimal)
2051 while ((unsigned char) *cmp2p == c && avail >= 0)
2052 if (*++cmp2p == '\0')
2053 break;
2054 else
2056 if (avail == 0 || inchar () == EOF)
2057 break;
2058 --avail;
2063 if (cmp2p != NULL && *cmp2p == '\0')
2065 /* Add all the characters. */
2066 for (cmpp = thousands; *cmpp != '\0'; ++cmpp)
2067 ADDW ((unsigned char) *cmpp);
2068 if (width > 0)
2069 width = avail;
2071 else
2073 /* The last read character is not part of the number
2074 anymore. */
2075 ungetc (c, s);
2076 break;
2079 #endif
2082 if (width == 0 || inchar () == EOF)
2083 break;
2085 if (width > 0)
2086 --width;
2089 wctrans_t map;
2090 if (__builtin_expect ((flags & I18N) != 0, 0)
2091 /* Hexadecimal floats make no sense, fixing localized
2092 digits with ASCII letters. */
2093 && !(flags & HEXA_FLOAT)
2094 /* Minimum requirement. */
2095 && (wpsize == 0 || got_dot)
2096 && (map = __wctrans ("to_inpunct")) != NULL)
2098 /* Reget the first character. */
2099 inchar ();
2101 /* Localized digits, decimal points, and thousands
2102 separator. */
2103 wint_t wcdigits[12];
2105 /* First get decimal equivalent to check if we read it
2106 or not. */
2107 wcdigits[11] = __towctrans (L'.', map);
2109 /* If we have not read any character or have just read
2110 locale decimal point which matches the decimal point
2111 for localized FP numbers, then we may have localized
2112 digits. Note, we test GOT_DOT above. */
2113 #ifdef COMPILE_WSCANF
2114 if (wpsize == 0 || (wpsize == 1 && wcdigits[11] == decimal))
2115 #else
2116 char mbdigits[12][MB_LEN_MAX + 1];
2118 mbstate_t state;
2119 memset (&state, '\0', sizeof (state));
2121 bool match_so_far = wpsize == 0;
2122 size_t mblen = __wcrtomb (mbdigits[11], wcdigits[11], &state);
2123 if (mblen != (size_t) -1)
2125 mbdigits[11][mblen] = '\0';
2126 match_so_far |= (wpsize == strlen (decimal)
2127 && strcmp (decimal, mbdigits[11]) == 0);
2129 else
2131 size_t decimal_len = strlen (decimal);
2132 /* This should always be the case but the data comes
2133 from a file. */
2134 if (decimal_len <= MB_LEN_MAX)
2136 match_so_far |= wpsize == decimal_len;
2137 memcpy (mbdigits[11], decimal, decimal_len + 1);
2139 else
2140 match_so_far = false;
2143 if (match_so_far)
2144 #endif
2146 bool have_locthousands = (flags & GROUP) != 0;
2148 /* Now get the digits and the thousands-sep equivalents. */
2149 for (int n = 0; n < 11; ++n)
2151 if (n < 10)
2152 wcdigits[n] = __towctrans (L'0' + n, map);
2153 else if (n == 10)
2155 wcdigits[10] = __towctrans (L',', map);
2156 have_locthousands &= wcdigits[10] != L'\0';
2159 #ifndef COMPILE_WSCANF
2160 memset (&state, '\0', sizeof (state));
2162 size_t mblen = __wcrtomb (mbdigits[n], wcdigits[n],
2163 &state);
2164 if (mblen == (size_t) -1)
2166 if (n == 10)
2168 if (have_locthousands)
2170 size_t thousands_len = strlen (thousands);
2171 if (thousands_len <= MB_LEN_MAX)
2172 memcpy (mbdigits[10], thousands,
2173 thousands_len + 1);
2174 else
2175 have_locthousands = false;
2178 else
2179 /* Ignore checking against localized digits. */
2180 goto no_i18nflt;
2182 else
2183 mbdigits[n][mblen] = '\0';
2184 #endif
2187 /* Start checking against localized digits, if
2188 convertion is done correctly. */
2189 while (1)
2191 if (got_e && wp[wpsize - 1] == exp_char
2192 && (c == L_('-') || c == L_('+')))
2193 ADDW (c);
2194 else if (wpsize > 0 && !got_e
2195 && (CHAR_T) TOLOWER (c) == exp_char)
2197 ADDW (exp_char);
2198 got_e = got_dot = 1;
2200 else
2202 /* Check against localized digits, decimal point,
2203 and thousands separator. */
2204 int n;
2205 for (n = 0; n < 12; ++n)
2207 #ifdef COMPILE_WSCANF
2208 if (c == wcdigits[n])
2210 if (n < 10)
2211 ADDW (L_('0') + n);
2212 else if (n == 11 && !got_dot)
2214 ADDW (decimal);
2215 got_dot = 1;
2217 else if (n == 10 && have_locthousands
2218 && ! got_dot)
2219 ADDW (thousands);
2220 else
2221 /* The last read character is not part
2222 of the number anymore. */
2223 n = 12;
2225 break;
2227 #else
2228 const char *cmpp = mbdigits[n];
2229 int avail = width > 0 ? width : INT_MAX;
2231 while ((unsigned char) *cmpp == c && avail >= 0)
2232 if (*++cmpp == '\0')
2233 break;
2234 else
2236 if (avail == 0 || inchar () == EOF)
2237 break;
2238 --avail;
2240 if (*cmpp == '\0')
2242 if (width > 0)
2243 width = avail;
2245 if (n < 10)
2246 ADDW (L_('0') + n);
2247 else if (n == 11 && !got_dot)
2249 /* Add all the characters. */
2250 for (cmpp = decimal; *cmpp != '\0';
2251 ++cmpp)
2252 ADDW ((unsigned char) *cmpp);
2254 got_dot = 1;
2256 else if (n == 10 && (flags & GROUP) != 0
2257 && ! got_dot)
2259 /* Add all the characters. */
2260 for (cmpp = thousands; *cmpp != '\0';
2261 ++cmpp)
2262 ADDW ((unsigned char) *cmpp);
2264 else
2265 /* The last read character is not part
2266 of the number anymore. */
2267 n = 12;
2269 break;
2272 /* We are pushing all read characters back. */
2273 if (cmpp > mbdigits[n])
2275 ungetc (c, s);
2276 while (--cmpp > mbdigits[n])
2277 ungetc_not_eof ((unsigned char) *cmpp, s);
2278 c = (unsigned char) *cmpp;
2280 #endif
2283 if (n >= 12)
2285 /* The last read character is not part
2286 of the number anymore. */
2287 ungetc (c, s);
2288 break;
2292 if (width == 0 || inchar () == EOF)
2293 break;
2295 if (width > 0)
2296 --width;
2300 #ifndef COMPILE_WSCANF
2301 no_i18nflt:
2303 #endif
2306 /* Have we read any character? If we try to read a number
2307 in hexadecimal notation and we have read only the `0x'
2308 prefix this is an error. */
2309 if (__builtin_expect (wpsize == 0
2310 || ((flags & HEXA_FLOAT) && wpsize == 2), 0))
2311 conv_error ();
2313 scan_float:
2314 /* Convert the number. */
2315 ADDW (L_('\0'));
2316 if ((flags & LONGDBL) && !__ldbl_is_dbl)
2318 long double d = __strtold_internal (wp, &tw, flags & GROUP);
2319 if (!(flags & SUPPRESS) && tw != wp)
2320 *ARG (long double *) = negative ? -d : d;
2322 else if (flags & (LONG | LONGDBL))
2324 double d = __strtod_internal (wp, &tw, flags & GROUP);
2325 if (!(flags & SUPPRESS) && tw != wp)
2326 *ARG (double *) = negative ? -d : d;
2328 else
2330 float d = __strtof_internal (wp, &tw, flags & GROUP);
2331 if (!(flags & SUPPRESS) && tw != wp)
2332 *ARG (float *) = negative ? -d : d;
2335 if (__builtin_expect (tw == wp, 0))
2336 conv_error ();
2338 if (!(flags & SUPPRESS))
2339 ++done;
2340 break;
2342 case L_('['): /* Character class. */
2343 if (flags & LONG)
2344 STRING_ARG (wstr, wchar_t, 100);
2345 else
2346 STRING_ARG (str, char, 100);
2348 if (*f == L_('^'))
2350 ++f;
2351 not_in = 1;
2353 else
2354 not_in = 0;
2356 if (width < 0)
2357 /* There is no width given so there is also no limit on the
2358 number of characters we read. Therefore we set width to
2359 a very high value to make the algorithm easier. */
2360 width = INT_MAX;
2362 #ifdef COMPILE_WSCANF
2363 /* Find the beginning and the end of the scanlist. We are not
2364 creating a lookup table since it would have to be too large.
2365 Instead we search each time through the string. This is not
2366 a constant lookup time but who uses this feature deserves to
2367 be punished. */
2368 tw = (wchar_t *) f; /* Marks the beginning. */
2370 if (*f == L']')
2371 ++f;
2373 while ((fc = *f++) != L'\0' && fc != L']');
2375 if (__builtin_expect (fc == L'\0', 0))
2376 conv_error ();
2377 wchar_t *twend = (wchar_t *) f - 1;
2378 #else
2379 /* Fill WP with byte flags indexed by character.
2380 We will use this flag map for matching input characters. */
2381 if (wpmax < UCHAR_MAX + 1)
2383 wpmax = UCHAR_MAX + 1;
2384 wp = (char *) alloca (wpmax);
2386 memset (wp, '\0', UCHAR_MAX + 1);
2388 fc = *f;
2389 if (fc == ']' || fc == '-')
2391 /* If ] or - appears before any char in the set, it is not
2392 the terminator or separator, but the first char in the
2393 set. */
2394 wp[fc] = 1;
2395 ++f;
2398 while ((fc = *f++) != '\0' && fc != ']')
2399 if (fc == '-' && *f != '\0' && *f != ']'
2400 && (unsigned char) f[-2] <= (unsigned char) *f)
2402 /* Add all characters from the one before the '-'
2403 up to (but not including) the next format char. */
2404 for (fc = (unsigned char) f[-2]; fc < (unsigned char) *f; ++fc)
2405 wp[fc] = 1;
2407 else
2408 /* Add the character to the flag map. */
2409 wp[fc] = 1;
2411 if (__builtin_expect (fc == '\0', 0))
2412 conv_error();
2413 #endif
2415 if (flags & LONG)
2417 size_t now = read_in;
2418 #ifdef COMPILE_WSCANF
2419 if (__builtin_expect (inchar () == WEOF, 0))
2420 input_error ();
2424 wchar_t *runp;
2426 /* Test whether it's in the scanlist. */
2427 runp = tw;
2428 while (runp < twend)
2430 if (runp[0] == L'-' && runp[1] != '\0'
2431 && runp + 1 != twend
2432 && runp != tw
2433 && (unsigned int) runp[-1] <= (unsigned int) runp[1])
2435 /* Match against all characters in between the
2436 first and last character of the sequence. */
2437 wchar_t wc;
2439 for (wc = runp[-1] + 1; wc <= runp[1]; ++wc)
2440 if ((wint_t) wc == c)
2441 break;
2443 if (wc <= runp[1] && !not_in)
2444 break;
2445 if (wc <= runp[1] && not_in)
2447 /* The current character is not in the
2448 scanset. */
2449 ungetc (c, s);
2450 goto out;
2453 runp += 2;
2455 else
2457 if ((wint_t) *runp == c && !not_in)
2458 break;
2459 if ((wint_t) *runp == c && not_in)
2461 ungetc (c, s);
2462 goto out;
2465 ++runp;
2469 if (runp == twend && !not_in)
2471 ungetc (c, s);
2472 goto out;
2475 if (!(flags & SUPPRESS))
2477 *wstr++ = c;
2479 if ((flags & MALLOC)
2480 && wstr == (wchar_t *) *strptr + strsize)
2482 /* Enlarge the buffer. */
2483 wstr = (wchar_t *) realloc (*strptr,
2484 (2 * strsize)
2485 * sizeof (wchar_t));
2486 if (wstr == NULL)
2488 /* Can't allocate that much. Last-ditch
2489 effort. */
2490 wstr = (wchar_t *)
2491 realloc (*strptr, (strsize + 1)
2492 * sizeof (wchar_t));
2493 if (wstr == NULL)
2495 if (flags & POSIX_MALLOC)
2497 done = EOF;
2498 goto errout;
2500 /* We lose. Oh well. Terminate the string
2501 and stop converting, so at least we don't
2502 skip any input. */
2503 ((wchar_t *) (*strptr))[strsize - 1] = L'\0';
2504 strptr = NULL;
2505 ++done;
2506 conv_error ();
2508 else
2510 *strptr = (char *) wstr;
2511 wstr += strsize;
2512 ++strsize;
2515 else
2517 *strptr = (char *) wstr;
2518 wstr += strsize;
2519 strsize *= 2;
2524 while (--width > 0 && inchar () != WEOF);
2525 out:
2526 #else
2527 char buf[MB_LEN_MAX];
2528 size_t cnt = 0;
2529 mbstate_t cstate;
2531 if (__builtin_expect (inchar () == EOF, 0))
2532 input_error ();
2534 memset (&cstate, '\0', sizeof (cstate));
2538 if (wp[c] == not_in)
2540 ungetc_not_eof (c, s);
2541 break;
2544 /* This is easy. */
2545 if (!(flags & SUPPRESS))
2547 size_t n;
2549 /* Convert it into a wide character. */
2550 buf[0] = c;
2551 n = __mbrtowc (wstr, buf, 1, &cstate);
2553 if (n == (size_t) -2)
2555 /* Possibly correct character, just not enough
2556 input. */
2557 ++cnt;
2558 assert (cnt < MB_CUR_MAX);
2559 continue;
2561 cnt = 0;
2563 ++wstr;
2564 if ((flags & MALLOC)
2565 && wstr == (wchar_t *) *strptr + strsize)
2567 /* Enlarge the buffer. */
2568 wstr = (wchar_t *) realloc (*strptr,
2569 (2 * strsize
2570 * sizeof (wchar_t)));
2571 if (wstr == NULL)
2573 /* Can't allocate that much. Last-ditch
2574 effort. */
2575 wstr = (wchar_t *)
2576 realloc (*strptr, ((strsize + 1)
2577 * sizeof (wchar_t)));
2578 if (wstr == NULL)
2580 if (flags & POSIX_MALLOC)
2582 done = EOF;
2583 goto errout;
2585 /* We lose. Oh well. Terminate the
2586 string and stop converting,
2587 so at least we don't skip any input. */
2588 ((wchar_t *) (*strptr))[strsize - 1] = L'\0';
2589 strptr = NULL;
2590 ++done;
2591 conv_error ();
2593 else
2595 *strptr = (char *) wstr;
2596 wstr += strsize;
2597 ++strsize;
2600 else
2602 *strptr = (char *) wstr;
2603 wstr += strsize;
2604 strsize *= 2;
2609 if (--width <= 0)
2610 break;
2612 while (inchar () != EOF);
2614 if (__builtin_expect (cnt != 0, 0))
2615 /* We stopped in the middle of recognizing another
2616 character. That's a problem. */
2617 encode_error ();
2618 #endif
2620 if (__builtin_expect (now == read_in, 0))
2621 /* We haven't succesfully read any character. */
2622 conv_error ();
2624 if (!(flags & SUPPRESS))
2626 *wstr++ = L'\0';
2628 if ((flags & MALLOC)
2629 && wstr - (wchar_t *) *strptr != strsize)
2631 wchar_t *cp = (wchar_t *)
2632 realloc (*strptr, ((wstr - (wchar_t *) *strptr)
2633 * sizeof(wchar_t)));
2634 if (cp != NULL)
2635 *strptr = (char *) cp;
2637 strptr = NULL;
2639 ++done;
2642 else
2644 size_t now = read_in;
2646 if (__builtin_expect (inchar () == EOF, 0))
2647 input_error ();
2649 #ifdef COMPILE_WSCANF
2651 memset (&state, '\0', sizeof (state));
2655 wchar_t *runp;
2656 size_t n;
2658 /* Test whether it's in the scanlist. */
2659 runp = tw;
2660 while (runp < twend)
2662 if (runp[0] == L'-' && runp[1] != '\0'
2663 && runp + 1 != twend
2664 && runp != tw
2665 && (unsigned int) runp[-1] <= (unsigned int) runp[1])
2667 /* Match against all characters in between the
2668 first and last character of the sequence. */
2669 wchar_t wc;
2671 for (wc = runp[-1] + 1; wc <= runp[1]; ++wc)
2672 if ((wint_t) wc == c)
2673 break;
2675 if (wc <= runp[1] && !not_in)
2676 break;
2677 if (wc <= runp[1] && not_in)
2679 /* The current character is not in the
2680 scanset. */
2681 ungetc (c, s);
2682 goto out2;
2685 runp += 2;
2687 else
2689 if ((wint_t) *runp == c && !not_in)
2690 break;
2691 if ((wint_t) *runp == c && not_in)
2693 ungetc (c, s);
2694 goto out2;
2697 ++runp;
2701 if (runp == twend && !not_in)
2703 ungetc (c, s);
2704 goto out2;
2707 if (!(flags & SUPPRESS))
2709 if ((flags & MALLOC)
2710 && str + MB_CUR_MAX >= *strptr + strsize)
2712 /* Enlarge the buffer. */
2713 size_t strleng = str - *strptr;
2714 char *newstr;
2716 newstr = (char *) realloc (*strptr, 2 * strsize);
2717 if (newstr == NULL)
2719 /* Can't allocate that much. Last-ditch
2720 effort. */
2721 newstr = (char *) realloc (*strptr,
2722 strleng + MB_CUR_MAX);
2723 if (newstr == NULL)
2725 if (flags & POSIX_MALLOC)
2727 done = EOF;
2728 goto errout;
2730 /* We lose. Oh well. Terminate the string
2731 and stop converting, so at least we don't
2732 skip any input. */
2733 ((char *) (*strptr))[strleng] = '\0';
2734 strptr = NULL;
2735 ++done;
2736 conv_error ();
2738 else
2740 *strptr = newstr;
2741 str = newstr + strleng;
2742 strsize = strleng + MB_CUR_MAX;
2745 else
2747 *strptr = newstr;
2748 str = newstr + strleng;
2749 strsize *= 2;
2754 n = __wcrtomb (!(flags & SUPPRESS) ? str : NULL, c, &state);
2755 if (__builtin_expect (n == (size_t) -1, 0))
2756 encode_error ();
2758 assert (n <= MB_CUR_MAX);
2759 str += n;
2761 while (--width > 0 && inchar () != WEOF);
2762 out2:
2763 #else
2766 if (wp[c] == not_in)
2768 ungetc_not_eof (c, s);
2769 break;
2772 /* This is easy. */
2773 if (!(flags & SUPPRESS))
2775 *str++ = c;
2776 if ((flags & MALLOC)
2777 && (char *) str == *strptr + strsize)
2779 /* Enlarge the buffer. */
2780 size_t newsize = 2 * strsize;
2782 allocagain:
2783 str = (char *) realloc (*strptr, newsize);
2784 if (str == NULL)
2786 /* Can't allocate that much. Last-ditch
2787 effort. */
2788 if (newsize > strsize + 1)
2790 newsize = strsize + 1;
2791 goto allocagain;
2793 if (flags & POSIX_MALLOC)
2795 done = EOF;
2796 goto errout;
2798 /* We lose. Oh well. Terminate the
2799 string and stop converting,
2800 so at least we don't skip any input. */
2801 ((char *) (*strptr))[strsize - 1] = '\0';
2802 strptr = NULL;
2803 ++done;
2804 conv_error ();
2806 else
2808 *strptr = (char *) str;
2809 str += strsize;
2810 strsize = newsize;
2815 while (--width > 0 && inchar () != EOF);
2816 #endif
2818 if (__builtin_expect (now == read_in, 0))
2819 /* We haven't succesfully read any character. */
2820 conv_error ();
2822 if (!(flags & SUPPRESS))
2824 #ifdef COMPILE_WSCANF
2825 /* We have to emit the code to get into the initial
2826 state. */
2827 char buf[MB_LEN_MAX];
2828 size_t n = __wcrtomb (buf, L'\0', &state);
2829 if (n > 0 && (flags & MALLOC)
2830 && str + n >= *strptr + strsize)
2832 /* Enlarge the buffer. */
2833 size_t strleng = str - *strptr;
2834 char *newstr;
2836 newstr = (char *) realloc (*strptr, strleng + n + 1);
2837 if (newstr == NULL)
2839 if (flags & POSIX_MALLOC)
2841 done = EOF;
2842 goto errout;
2844 /* We lose. Oh well. Terminate the string
2845 and stop converting, so at least we don't
2846 skip any input. */
2847 ((char *) (*strptr))[strleng] = '\0';
2848 strptr = NULL;
2849 ++done;
2850 conv_error ();
2852 else
2854 *strptr = newstr;
2855 str = newstr + strleng;
2856 strsize = strleng + n + 1;
2860 str = __mempcpy (str, buf, n);
2861 #endif
2862 *str++ = '\0';
2864 if ((flags & MALLOC) && str - *strptr != strsize)
2866 char *cp = (char *) realloc (*strptr, str - *strptr);
2867 if (cp != NULL)
2868 *strptr = cp;
2870 strptr = NULL;
2872 ++done;
2875 break;
2877 case L_('p'): /* Generic pointer. */
2878 base = 16;
2879 /* A PTR must be the same size as a `long int'. */
2880 flags &= ~(SHORT|LONGDBL);
2881 if (need_long)
2882 flags |= LONG;
2883 flags |= READ_POINTER;
2884 goto number;
2886 default:
2887 /* If this is an unknown format character punt. */
2888 conv_error ();
2892 /* The last thing we saw int the format string was a white space.
2893 Consume the last white spaces. */
2894 if (skip_space)
2897 c = inchar ();
2898 while (ISSPACE (c));
2899 ungetc (c, s);
2902 errout:
2903 /* Unlock stream. */
2904 UNLOCK_STREAM (s);
2906 if (use_malloc)
2907 free (wp);
2909 if (errp != NULL)
2910 *errp |= errval;
2912 if (__builtin_expect (done == EOF, 0))
2914 if (__builtin_expect (ptrs_to_free != NULL, 0))
2916 struct ptrs_to_free *p = ptrs_to_free;
2917 while (p != NULL)
2919 for (size_t cnt = 0; cnt < p->count; ++cnt)
2921 free (*p->ptrs[cnt]);
2922 *p->ptrs[cnt] = NULL;
2924 p = p->next;
2925 ptrs_to_free = p;
2929 else if (__builtin_expect (strptr != NULL, 0))
2931 free (*strptr);
2932 *strptr = NULL;
2934 return done;
2937 #ifdef COMPILE_WSCANF
2939 __vfwscanf (FILE *s, const wchar_t *format, va_list argptr)
2941 return _IO_vfwscanf (s, format, argptr, NULL);
2943 ldbl_weak_alias (__vfwscanf, vfwscanf)
2944 #else
2946 ___vfscanf (FILE *s, const char *format, va_list argptr)
2948 return _IO_vfscanf_internal (s, format, argptr, NULL);
2950 ldbl_strong_alias (_IO_vfscanf_internal, _IO_vfscanf)
2951 ldbl_hidden_def (_IO_vfscanf_internal, _IO_vfscanf)
2952 ldbl_strong_alias (___vfscanf, __vfscanf)
2953 ldbl_hidden_def (___vfscanf, __vfscanf)
2954 ldbl_weak_alias (___vfscanf, vfscanf)
2955 #endif