1 /* Copyright (C) 1991-1999, 2000, 2001 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 Library General Public License as
6 published by the Free Software Foundation; either version 2 of the
7 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 Library General Public License for more details.
14 You should have received a copy of the GNU Library General Public
15 License along with the GNU C Library; see the file COPYING.LIB. If not,
16 write to the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
17 Boston, MA 02111-1307, USA. */
30 #include <bits/libc-lock.h>
31 #include <locale/localeinfo.h>
34 # define HAVE_LONGLONG
35 # define LONGLONG long long
37 # define LONGLONG long
40 /* Determine whether we have to handle `long long' at all. */
41 #if LONG_MAX == LONG_LONG_MAX
42 # define need_longlong 0
44 # define need_longlong 1
47 /* Determine whether we have to handle `long'. */
48 #if INT_MAX == LONG_MAX
54 /* Those are flags in the conversion format. */
55 #define LONG 0x001 /* l: long or double */
56 #define LONGDBL 0x002 /* L: long long or long double */
57 #define SHORT 0x004 /* h: short */
58 #define SUPPRESS 0x008 /* *: suppress assignment */
59 #define POINTER 0x010 /* weird %p pointer (`fake hex') */
60 #define NOSKIP 0x020 /* do not skip blanks */
61 #define WIDTH 0x040 /* width was given */
62 #define GROUP 0x080 /* ': group numbers */
63 #define MALLOC 0x100 /* a: malloc strings */
64 #define CHAR 0x200 /* hh: char */
65 #define I18N 0x400 /* I: use locale's digits */
73 # define va_list _IO_va_list
75 # ifdef COMPILE_WSCANF
76 # define ungetc(c, s) ((void) (c == WEOF \
78 _IO_sputbackwc (s, c))))
79 # define ungetc_not_eof(c, s) ((void) (--read_in, \
80 _IO_sputbackwc (s, c)))
81 # define inchar() (c == WEOF ? WEOF \
82 : ((c = _IO_getwc_unlocked (s)), \
83 (void) (c != WEOF && ++read_in), c))
85 # define MEMCPY(d, s, n) __wmemcpy (d, s, n)
86 # define ISSPACE(Ch) iswspace (Ch)
87 # define ISDIGIT(Ch) iswdigit (Ch)
88 # define ISXDIGIT(Ch) iswxdigit (Ch)
89 # define TOLOWER(Ch) towlower (Ch)
90 # define ORIENT if (_IO_fwide (s, 1) != 1) return WEOF
91 # define __strtoll_internal __wcstoll_internal
92 # define __strtoull_internal __wcstoull_internal
93 # define __strtol_internal __wcstol_internal
94 # define __strtoul_internal __wcstoul_internal
95 # define __strtold_internal __wcstold_internal
96 # define __strtod_internal __wcstod_internal
97 # define __strtof_internal __wcstof_internal
99 # define L_(Str) L##Str
100 # define CHAR_T wchar_t
101 # define UCHAR_T unsigned int
102 # define WINT_T wint_t
106 # define ungetc(c, s) ((void) ((int) c == EOF \
108 _IO_sputbackc (s, (unsigned char) c))))
109 # define ungetc_not_eof(c, s) ((void) (--read_in, \
110 _IO_sputbackc (s, (unsigned char) c)))
111 # define inchar() (c == EOF ? EOF \
112 : ((c = _IO_getc_unlocked (s)), \
113 (void) (c != EOF && ++read_in), c))
114 # define MEMCPY(d, s, n) memcpy (d, s, n)
115 # define ISSPACE(Ch) isspace (Ch)
116 # define ISDIGIT(Ch) isdigit (Ch)
117 # define ISXDIGIT(Ch) isxdigit (Ch)
118 # define TOLOWER(Ch) tolower (Ch)
119 # define ORIENT if (s->_vtable_offset == 0 \
120 && _IO_fwide (s, -1) != -1) \
125 # define UCHAR_T unsigned char
129 # define encode_error() do { \
130 if (errp != NULL) *errp |= 4; \
131 _IO_funlockfile (s); \
132 __libc_cleanup_end (0); \
133 __set_errno (EILSEQ); \
136 # define conv_error() do { \
137 if (errp != NULL) *errp |= 2; \
138 _IO_funlockfile (s); \
139 __libc_cleanup_end (0); \
142 # define input_error() do { \
143 _IO_funlockfile (s); \
144 if (errp != NULL) *errp |= 1; \
145 __libc_cleanup_end (0); \
146 return done ?: EOF; \
148 # define memory_error() do { \
149 _IO_funlockfile (s); \
150 __set_errno (ENOMEM); \
151 __libc_cleanup_end (0); \
154 # define ARGCHECK(s, format) \
157 /* Check file argument for consistence. */ \
158 CHECK_FILE (s, EOF); \
159 if (s->_flags & _IO_NO_READS) \
161 __set_errno (EBADF); \
164 else if (format == NULL) \
170 # define LOCK_STREAM(S) \
171 __libc_cleanup_region_start ((void (*) (void *)) &_IO_funlockfile, (S)); \
173 # define UNLOCK_STREAM(S) \
174 _IO_funlockfile (S); \
175 __libc_cleanup_region_end (0)
177 # define ungetc(c, s) ((void) (c != EOF && --read_in), ungetc (c, s))
178 # define ungetc_not_eof(c, s) (--read_in, (ungetc) (c, s))
179 # define inchar() (c == EOF ? EOF \
180 : ((c = getc (s)), (void) (c != EOF && ++read_in), c))
181 # define MEMCPY(d, s, n) memcpy (d, s, n)
182 # define ISSPACE(Ch) isspace (Ch)
183 # define ISDIGIT(Ch) isdigit (Ch)
184 # define ISXDIGIT(Ch) isxdigit (Ch)
185 # define TOLOWER(Ch) tolower (Ch)
189 # define UCHAR_T unsigned char
192 # define encode_error() do { \
194 __set_errno (EILSEQ); \
197 # define conv_error() do { \
201 # define input_error() do { \
203 return done ?: EOF; \
205 # define memory_error() do { \
207 __set_errno (ENOMEM); \
210 # define ARGCHECK(s, format) \
213 /* Check file argument for consistence. */ \
214 if (!__validfp (s) || !s->__mode.__read) \
216 __set_errno (EBADF); \
219 else if (format == NULL) \
221 __set_errno (EINVAL); \
226 /* XXX For now !!! */
227 # define flockfile(S) /* nothing */
228 # define funlockfile(S) /* nothing */
229 # define LOCK_STREAM(S)
230 # define UNLOCK_STREAM(S)
232 # define LOCK_STREAM(S) \
233 __libc_cleanup_region_start (&__funlockfile, (S)); \
235 # define UNLOCK_STREAM(S) \
237 __libc_cleanup_region_end (0)
242 /* Read formatted input from S according to the format string
243 FORMAT, using the argument list in ARG.
244 Return the number of assignments made, or -1 for an input error. */
246 # ifdef COMPILE_WSCANF
248 _IO_vfwscanf (s
, format
, argptr
, errp
)
250 const wchar_t *format
;
255 _IO_vfscanf (s
, format
, argptr
, errp
)
263 __vfscanf (FILE *s
, const char *format
, va_list argptr
)
267 register const CHAR_T
*f
= format
;
268 register UCHAR_T fc
; /* Current character of the format. */
269 register WINT_T done
= 0; /* Assignments done. */
270 register size_t read_in
= 0; /* Chars read in. */
271 register WINT_T c
= 0; /* Last char read. */
272 register int width
; /* Maximum field width. */
273 register int flags
; /* Modifiers for current format element. */
275 /* Status for reading F-P nums. */
276 char got_dot
, got_e
, negative
;
277 /* If a [...] is a [^...]. */
279 #define exp_char not_in
280 /* Base for integral numbers. */
282 /* Signedness for integral numbers. */
284 #define is_hexa number_signed
285 /* Decimal point character. */
286 #ifdef COMPILE_WSCANF
291 /* The thousands character of the current locale. */
292 #ifdef COMPILE_WSCANF
295 const char *thousands
;
297 /* State for the conversions. */
299 /* Integral holding variables. */
303 unsigned long long int uq
;
305 unsigned long int ul
;
307 /* Character-buffer pointer. */
309 wchar_t *wstr
= NULL
;
310 char **strptr
= NULL
;
312 /* We must not react on white spaces immediately because they can
313 possibly be matched even if in the input stream no character is
314 available anymore. */
316 /* Nonzero if we are reading a pointer. */
319 CHAR_T
*tw
; /* Temporary pointer. */
320 CHAR_T
*wp
= NULL
; /* Workspace. */
321 size_t wpmax
= 0; /* Maximal size of workspace. */
322 size_t wpsize
; /* Currently used bytes in workspace. */
326 if (wpsize == wpmax) \
329 wpmax = (UCHAR_MAX + 1 > 2 * wpmax ? UCHAR_MAX + 1 : 2 * wpmax); \
330 wp = (CHAR_T *) alloca (wpmax * sizeof (wchar_t)); \
332 MEMCPY (wp, old, wpsize); \
334 wp[wpsize++] = (Ch); \
339 __va_copy (arg
, argptr
);
341 arg
= (va_list) argptr
;
348 ARGCHECK (s
, format
);
350 /* Figure out the decimal point character. */
351 #ifdef COMPILE_WSCANF
352 decimal
= _NL_CURRENT_WORD (LC_NUMERIC
, _NL_NUMERIC_DECIMAL_POINT_WC
);
354 decimal
= _NL_CURRENT (LC_NUMERIC
, DECIMAL_POINT
);
356 /* Figure out the thousands separator character. */
357 #ifdef COMPILE_WSCANF
358 thousands
= _NL_CURRENT_WORD (LC_NUMERIC
, _NL_NUMERIC_THOUSANDS_SEP_WC
);
360 thousands
= _NL_CURRENT (LC_NUMERIC
, THOUSANDS_SEP
);
361 if (*thousands
== '\0')
365 /* Lock the stream. */
369 #ifndef COMPILE_WSCANF
370 /* From now on we use `state' to convert the format string. */
371 memset (&state
, '\0', sizeof (state
));
374 /* Run through the format string. */
378 /* Extract the next argument, which is of type TYPE.
379 For a %N$... spec, this is the Nth argument from the beginning;
380 otherwise it is the next argument after the state now in ARG. */
382 # define ARG(type) (argpos == 0 ? va_arg (arg, type) : \
383 ({ unsigned int pos = argpos; \
385 __va_copy (arg, argptr); \
387 (void) va_arg (arg, void *); \
388 va_arg (arg, type); \
392 /* XXX Possible optimization. */
393 # define ARG(type) (argpos == 0 ? va_arg (arg, type) : \
394 ({ va_list arg = (va_list) argptr; \
395 arg = (va_list) ((char *) arg \
397 * __va_rounded_size (void *)); \
398 va_arg (arg, type); \
401 # define ARG(type) (argpos == 0 ? va_arg (arg, type) : \
402 ({ unsigned int pos = argpos; \
403 va_list arg = (va_list) argptr; \
405 (void) va_arg (arg, void *); \
406 va_arg (arg, type); \
411 #ifndef COMPILE_WSCANF
412 if (!isascii ((unsigned char) *f
))
414 /* Non-ASCII, may be a multibyte. */
415 int len
= __mbrlen (f
, strlen (f
), &state
);
423 else if (c
!= (unsigned char) *f
++)
425 ungetc_not_eof (c
, s
);
438 /* Remember to skip spaces. */
445 /* Read a character. */
448 /* Characters other than format specs must just match. */
452 /* We saw white space char as the last character in the format
453 string. Now it's time to skip all leading white space. */
457 if (inchar () == EOF
&& errno
== EINTR
)
471 /* This is the start of the conversion string. */
474 /* Not yet decided whether we read a pointer or not. */
477 /* Initialize state of modifiers. */
480 /* Prepare temporary buffer. */
483 /* Check for a positional parameter specification. */
484 if (ISDIGIT ((UCHAR_T
) *f
))
486 argpos
= (UCHAR_T
) *f
++ - L_('0');
487 while (ISDIGIT ((UCHAR_T
) *f
))
488 argpos
= argpos
* 10 + ((UCHAR_T
) *f
++ - L_('0'));
493 /* Oops; that was actually the field width. */
501 /* Check for the assignment-suppressing, the number grouping flag,
502 and the signal to use the locale's digit representation. */
503 while (*f
== L_('*') || *f
== L_('\'') || *f
== L_('I'))
517 /* We have seen width. */
518 if (ISDIGIT ((UCHAR_T
) *f
))
521 /* Find the maximum field width. */
523 while (ISDIGIT ((UCHAR_T
) *f
))
526 width
+= (UCHAR_T
) *f
++ - L_('0');
532 /* Check for type modifiers. */
536 /* ints are short ints or chars. */
548 /* A double `l' is equivalent to an `L'. */
550 flags
|= LONGDBL
| LONG
;
553 /* ints are long ints. */
558 /* doubles are long doubles, and ints are long long ints. */
559 flags
|= LONGDBL
| LONG
;
562 /* The `a' is used as a flag only if followed by `s', `S' or
564 if (*f
!= L_('s') && *f
!= L_('S') && *f
!= L_('['))
569 /* String conversions (%s, %[) take a `char **'
570 arg and fill it in with a malloc'd pointer. */
574 if (need_longlong
&& sizeof (size_t) > sizeof (unsigned long int))
576 else if (sizeof (size_t) > sizeof (unsigned int))
580 if (need_longlong
&& sizeof (uintmax_t) > sizeof (unsigned long int))
582 else if (sizeof (uintmax_t) > sizeof (unsigned int))
586 if (need_longlong
&& sizeof (ptrdiff_t) > sizeof (long int))
588 else if (sizeof (ptrdiff_t) > sizeof (int))
592 /* Not a recognized modifier. Backup. */
597 /* End of the format string? */
601 /* Find the conversion specifier. */
603 if (skip_space
|| (fc
!= L_('[') && fc
!= L_('c')
604 && fc
!= L_('C') && fc
!= L_('n')))
606 /* Eat whitespace. */
607 int save_errno
= errno
;
610 if (inchar () == EOF
&& errno
== EINTR
)
620 case L_('%'): /* Must match a literal '%'. */
626 ungetc_not_eof (c
, s
);
631 case L_('n'): /* Answer number of assignments done. */
632 /* Corrigendum 1 to ISO C 1990 describes the allowed flags
633 with the 'n' conversion specifier. */
634 if (!(flags
& SUPPRESS
))
636 /* Don't count the read-ahead. */
637 if (need_longlong
&& (flags
& LONGDBL
))
638 *ARG (long long int *) = read_in
;
639 else if (need_long
&& (flags
& LONG
))
640 *ARG (long int *) = read_in
;
641 else if (flags
& SHORT
)
642 *ARG (short int *) = read_in
;
643 else if (!(flags
& CHAR
))
644 *ARG (int *) = read_in
;
646 *ARG (char *) = read_in
;
648 #ifdef NO_BUG_IN_ISO_C_CORRIGENDUM_1
649 /* We have a severe problem here. The ISO C standard
650 contradicts itself in explaining the effect of the %n
651 format in `scanf'. While in ISO C:1990 and the ISO C
652 Amendement 1:1995 the result is described as
654 Execution of a %n directive does not effect the
655 assignment count returned at the completion of
656 execution of the f(w)scanf function.
658 in ISO C Corrigendum 1:1994 the following was added:
661 Add the following fourth example:
664 int d1, d2, n1, n2, i;
665 i = sscanf("123", "%d%n%n%d", &d1, &n1, &n2, &d2);
666 the value 123 is assigned to d1 and the value3 to n1.
667 Because %n can never get an input failure the value
668 of 3 is also assigned to n2. The value of d2 is not
669 affected. The value 3 is assigned to i.
671 We go for now with the historically correct code from ISO C,
672 i.e., we don't count the %n assignments. When it ever
673 should proof to be wrong just remove the #ifdef above. */
679 case L_('c'): /* Match characters. */
680 if ((flags
& LONG
) == 0)
682 if (!(flags
& SUPPRESS
))
696 #ifdef COMPILE_WSCANF
697 /* We have to convert the wide character(s) into multibyte
698 characters and store the result. */
699 memset (&state
, '\0', sizeof (state
));
705 n
= __wcrtomb (!(flags
& SUPPRESS
) ? str
: NULL
, c
, &state
);
706 if (n
== (size_t) -1)
707 /* No valid wide character. */
710 /* Increment the output pointer. Even if we don't
714 while (--width
> 0 && inchar () != EOF
);
716 if (!(flags
& SUPPRESS
))
720 while (--width
> 0 && inchar () != EOF
);
723 while (--width
> 0 && inchar () != EOF
);
726 if (!(flags
& SUPPRESS
))
733 if (!(flags
& SUPPRESS
))
735 wstr
= ARG (wchar_t *);
744 #ifdef COMPILE_WSCANF
745 /* Just store the incoming wide characters. */
746 if (!(flags
& SUPPRESS
))
750 while (--width
> 0 && inchar () != EOF
);
753 while (--width
> 0 && inchar () != EOF
);
756 /* We have to convert the multibyte input sequence to wide
758 char buf
[MB_LEN_MAX
];
761 memset (&cstate
, '\0', sizeof (cstate
));
767 /* This is what we present the mbrtowc function first. */
775 n
= __mbrtowc (!(flags
& SUPPRESS
) ? wstr
: NULL
,
778 if (n
== (size_t) -2)
780 /* Possibly correct character, just not enough
782 assert (cnt
< MB_CUR_MAX
);
784 if (inchar () == EOF
)
794 /* We have a match. */
798 /* Advance the result pointer. */
801 while (--width
> 0 && inchar () != EOF
);
805 if (!(flags
& SUPPRESS
))
810 case L_('s'): /* Read a string. */
813 #define STRING_ARG(Str, Type) \
814 do if (!(flags & SUPPRESS)) \
816 if (flags & MALLOC) \
818 /* The string is to be stored in a malloc'd buffer. */ \
819 strptr = ARG (char **); \
820 if (strptr == NULL) \
822 /* Allocate an initial buffer. */ \
824 *strptr = (char *) malloc (strsize * sizeof (Type)); \
825 Str = (Type *) *strptr; \
828 Str = ARG (Type *); \
832 STRING_ARG (str
, char);
838 #ifdef COMPILE_WSCANF
839 memset (&state
, '\0', sizeof (state
));
846 ungetc_not_eof (c
, s
);
850 #ifdef COMPILE_WSCANF
851 /* This is quite complicated. We have to convert the
852 wide characters into multibyte characters and then
857 if (!(flags
& SUPPRESS
) && (flags
& MALLOC
)
858 && str
+ MB_CUR_MAX
>= *strptr
+ strsize
)
860 /* We have to enlarge the buffer if the `a' flag
862 size_t strleng
= str
- *strptr
;
865 newstr
= (char *) realloc (*strptr
, strsize
* 2);
868 /* Can't allocate that much. Last-ditch
870 newstr
= (char *) realloc (*strptr
,
871 strleng
+ MB_CUR_MAX
);
874 /* We lose. Oh well. Terminate the
875 string and stop converting,
876 so at least we don't skip any input. */
877 ((char *) (*strptr
))[strleng
] = '\0';
884 str
= newstr
+ strleng
;
885 strsize
= strleng
+ MB_CUR_MAX
;
891 str
= newstr
+ strleng
;
896 n
= __wcrtomb (!(flags
& SUPPRESS
) ? str
: NULL
, c
,
898 if (n
== (size_t) -1)
901 assert (n
<= MB_CUR_MAX
);
906 if (!(flags
& SUPPRESS
))
910 && (char *) str
== *strptr
+ strsize
)
912 /* Enlarge the buffer. */
913 str
= (char *) realloc (*strptr
, 2 * strsize
);
916 /* Can't allocate that much. Last-ditch
918 str
= (char *) realloc (*strptr
, strsize
+ 1);
921 /* We lose. Oh well. Terminate the
922 string and stop converting,
923 so at least we don't skip any input. */
924 ((char *) (*strptr
))[strsize
- 1] = '\0';
930 *strptr
= (char *) str
;
937 *strptr
= (char *) str
;
945 while ((width
<= 0 || --width
> 0) && inchar () != EOF
);
947 if (!(flags
& SUPPRESS
))
949 #ifdef COMPILE_WSCANF
950 /* We have to emit the code to get into the initial
952 char buf
[MB_LEN_MAX
];
953 size_t n
= __wcrtomb (buf
, L
'\0', &state
);
954 if (n
> 0 && (flags
& MALLOC
)
955 && str
+ n
>= *strptr
+ strsize
)
957 /* Enlarge the buffer. */
958 size_t strleng
= str
- *strptr
;
961 newstr
= (char *) realloc (*strptr
, strleng
+ n
+ 1);
964 /* We lose. Oh well. Terminate the string
965 and stop converting, so at least we don't
967 ((char *) (*strptr
))[strleng
] = '\0';
974 str
= newstr
+ strleng
;
975 strsize
= strleng
+ n
+ 1;
979 str
= __mempcpy (str
, buf
, n
);
983 if ((flags
& MALLOC
) && str
- *strptr
!= strsize
)
985 char *cp
= (char *) realloc (*strptr
, str
- *strptr
);
998 #ifndef COMPILE_WSCANF
1002 /* Wide character string. */
1003 STRING_ARG (wstr
, wchar_t);
1009 #ifndef COMPILE_WSCANF
1010 memset (&cstate
, '\0', sizeof (cstate
));
1017 ungetc_not_eof (c
, s
);
1021 #ifdef COMPILE_WSCANF
1023 if (!(flags
& SUPPRESS
))
1026 if ((flags
& MALLOC
)
1027 && wstr
== (wchar_t *) *strptr
+ strsize
)
1029 /* Enlarge the buffer. */
1030 wstr
= (wchar_t *) realloc (*strptr
,
1032 * sizeof (wchar_t));
1035 /* Can't allocate that much. Last-ditch
1037 wstr
= (wchar_t *) realloc (*strptr
,
1039 * sizeof (wchar_t));
1042 /* We lose. Oh well. Terminate the string
1043 and stop converting, so at least we don't
1045 ((wchar_t *) (*strptr
))[strsize
- 1] = L
'\0';
1051 *strptr
= (char *) wstr
;
1058 *strptr
= (char *) wstr
;
1066 char buf
[MB_LEN_MAX
];
1076 n
= __mbrtowc (!(flags
& SUPPRESS
) ? wstr
: NULL
,
1079 if (n
== (size_t) -2)
1081 /* Possibly correct character, just not enough
1083 assert (cnt
< MB_CUR_MAX
);
1085 if (inchar () == EOF
)
1095 /* We have a match. */
1099 if (!(flags
& SUPPRESS
) && (flags
& MALLOC
)
1100 && wstr
== (wchar_t *) *strptr
+ strsize
)
1102 /* Enlarge the buffer. */
1103 wstr
= (wchar_t *) realloc (*strptr
,
1105 * sizeof (wchar_t)));
1108 /* Can't allocate that much. Last-ditch effort. */
1109 wstr
= (wchar_t *) realloc (*strptr
,
1111 * sizeof (wchar_t)));
1114 /* We lose. Oh well. Terminate the
1115 string and stop converting, so at
1116 least we don't skip any input. */
1117 ((wchar_t *) (*strptr
))[strsize
- 1] = L
'\0';
1123 *strptr
= (char *) wstr
;
1130 *strptr
= (char *) wstr
;
1138 while ((width
<= 0 || --width
> 0) && inchar () != EOF
);
1140 if (!(flags
& SUPPRESS
))
1144 if ((flags
& MALLOC
) && wstr
- (wchar_t *) *strptr
!= strsize
)
1146 wchar_t *cp
= (wchar_t *) realloc (*strptr
,
1148 - (wchar_t *) *strptr
)
1149 * sizeof(wchar_t)));
1151 *strptr
= (char *) cp
;
1159 case L_('x'): /* Hexadecimal integer. */
1160 case L_('X'): /* Ditto. */
1165 case L_('o'): /* Octal integer. */
1170 case L_('u'): /* Unsigned decimal integer. */
1175 case L_('d'): /* Signed decimal integer. */
1180 case L_('i'): /* Generic number. */
1189 /* Check for a sign. */
1190 if (c
== L_('-') || c
== L_('+'))
1198 /* Look for a leading indication of base. */
1199 if (width
!= 0 && c
== L_('0'))
1207 if (width
!= 0 && TOLOWER (c
) == L_('x'))
1225 if (base
== 10 && (flags
& I18N
) != 0)
1230 #ifdef COMPILE_WSCANF
1231 const wchar_t *wcdigits
[10];
1233 const char *mbdigits
[10];
1238 #ifdef COMPILE_WSCANF
1239 to_level
= _NL_CURRENT_WORD (LC_CTYPE
,
1240 _NL_CTYPE_INDIGITS_WC_LEN
) - 1;
1242 to_level
= _NL_CURRENT_WORD (LC_CTYPE
,
1243 _NL_CTYPE_INDIGITS_MB_LEN
) - 1;
1246 /* Read the number into workspace. */
1247 while (c
!= EOF
&& width
!= 0)
1249 /* In this round we get the pointer to the digit strings
1250 and also perform the first round of comparisons. */
1251 for (n
= 0; n
< 10; ++n
)
1253 /* Get the string for the digits with value N. */
1254 #ifdef COMPILE_WSCANF
1255 wcdigits
[n
] = (const wchar_t *)
1256 _NL_CURRENT (LC_CTYPE
, _NL_CTYPE_INDIGITS0_WC
+ n
);
1257 wcdigits
[n
] += from_level
;
1259 if (c
== *wcdigits
[n
])
1261 to_level
= from_level
;
1265 /* Advance the pointer to the next string. */
1269 int avail
= width
> 0 ? width
: INT_MAX
;
1271 mbdigits
[n
] = _NL_CURRENT (LC_CTYPE
,
1272 _NL_CTYPE_INDIGITS0_MB
+ n
);
1274 for (level
= 0; level
< from_level
; level
++)
1275 mbdigits
[n
] = strchr (mbdigits
[n
], '\0') + 1;
1278 while ((unsigned char) *cmpp
== c
&& avail
> 0)
1280 if (*++cmpp
== '\0')
1284 if ((c
= inchar ()) == EOF
)
1294 to_level
= from_level
;
1298 /* We are pushing all read characters back. */
1299 if (cmpp
> mbdigits
[n
])
1302 while (--cmpp
> mbdigits
[n
])
1303 ungetc_not_eof ((unsigned char) *cmpp
, s
);
1304 c
= (unsigned char) *cmpp
;
1307 /* Advance the pointer to the next string. */
1308 mbdigits
[n
] = strchr (mbdigits
[n
], '\0') + 1;
1314 /* Have not yet found the digit. */
1315 for (level
= from_level
+ 1; level
<= to_level
; ++level
)
1317 /* Search all ten digits of this level. */
1318 for (n
= 0; n
< 10; ++n
)
1320 #ifdef COMPILE_WSCANF
1321 if (c
== *wcdigits
[n
])
1324 /* Advance the pointer to the next string. */
1328 int avail
= width
> 0 ? width
: INT_MAX
;
1331 while ((unsigned char) *cmpp
== c
&& avail
> 0)
1333 if (*++cmpp
== '\0')
1337 if ((c
= inchar ()) == EOF
)
1350 /* We are pushing all read characters back. */
1351 if (cmpp
> mbdigits
[n
])
1354 while (--cmpp
> mbdigits
[n
])
1355 ungetc_not_eof ((unsigned char) *cmpp
, s
);
1356 c
= (unsigned char) *cmpp
;
1359 /* Advance the pointer to the next string. */
1360 mbdigits
[n
] = strchr (mbdigits
[n
], '\0') + 1;
1376 else if ((flags
& GROUP
)
1377 #ifdef COMPILE_WSCANF
1378 && thousands
!= L
'\0'
1380 && thousands
!= NULL
1384 /* Try matching against the thousands separator. */
1385 #ifdef COMPILE_WSCANF
1389 const char *cmpp
= thousands
;
1390 int avail
= width
> 0 ? width
: INT_MAX
;
1392 while ((unsigned char) *cmpp
== c
&& avail
> 0)
1395 if (*++cmpp
== '\0')
1399 if ((c
= inchar ()) == EOF
)
1407 /* We are pushing all read characters back. */
1408 if (cmpp
> thousands
)
1410 wpsize
-= cmpp
- thousands
;
1412 while (--cmpp
> thousands
)
1413 ungetc_not_eof ((unsigned char) *cmpp
, s
);
1414 c
= (unsigned char) *cmpp
;
1422 /* The last thousands character will be added back by
1438 /* Read the number into workspace. */
1439 while (c
!= EOF
&& width
!= 0)
1446 else if (!ISDIGIT (c
) || c
- L_('0') >= base
)
1448 if (base
== 10 && (flags
& GROUP
)
1449 #ifdef COMPILE_WSCANF
1450 && thousands
!= L
'\0'
1452 && thousands
!= NULL
1456 /* Try matching against the thousands separator. */
1457 #ifdef COMPILE_WSCANF
1461 const char *cmpp
= thousands
;
1462 int avail
= width
> 0 ? width
: INT_MAX
;
1464 while ((unsigned char) *cmpp
== c
&& avail
> 0)
1467 if (*++cmpp
== '\0')
1471 if ((c
= inchar ()) == EOF
)
1479 /* We are pushing all read characters back. */
1480 if (cmpp
> thousands
)
1482 wpsize
-= cmpp
- thousands
;
1484 while (--cmpp
> thousands
)
1485 ungetc_not_eof ((unsigned char) *cmpp
, s
);
1486 c
= (unsigned char) *cmpp
;
1494 /* The last thousands character will be added back by
1510 || (wpsize
== 1 && (wp
[0] == L_('+') || wp
[0] == L_('-'))))
1512 /* There was no number. If we are supposed to read a pointer
1513 we must recognize "(nil)" as well. */
1514 if (wpsize
== 0 && read_pointer
&& (width
< 0 || width
>= 0)
1516 && TOLOWER (inchar ()) == L_('n')
1517 && TOLOWER (inchar ()) == L_('i')
1518 && TOLOWER (inchar ()) == L_('l')
1519 && inchar () == L_(')'))
1520 /* We must produce the value of a NULL pointer. A single
1521 '0' digit is enough. */
1525 /* The last read character is not part of the number
1533 /* The just read character is not part of the number anymore. */
1536 /* Convert the number. */
1538 if (need_longlong
&& (flags
& LONGDBL
))
1541 num
.q
= __strtoll_internal (wp
, &tw
, base
, flags
& GROUP
);
1543 num
.uq
= __strtoull_internal (wp
, &tw
, base
, flags
& GROUP
);
1548 num
.l
= __strtol_internal (wp
, &tw
, base
, flags
& GROUP
);
1550 num
.ul
= __strtoul_internal (wp
, &tw
, base
, flags
& GROUP
);
1555 if (!(flags
& SUPPRESS
))
1557 if (! number_signed
)
1559 if (need_longlong
&& (flags
& LONGDBL
))
1560 *ARG (unsigned LONGLONG
int *) = num
.uq
;
1561 else if (need_long
&& (flags
& LONG
))
1562 *ARG (unsigned long int *) = num
.ul
;
1563 else if (flags
& SHORT
)
1564 *ARG (unsigned short int *)
1565 = (unsigned short int) num
.ul
;
1566 else if (!(flags
& CHAR
))
1567 *ARG (unsigned int *) = (unsigned int) num
.ul
;
1569 *ARG (unsigned char *) = (unsigned char) num
.ul
;
1573 if (need_longlong
&& (flags
& LONGDBL
))
1574 *ARG (LONGLONG
int *) = num
.q
;
1575 else if (need_long
&& (flags
& LONG
))
1576 *ARG (long int *) = num
.l
;
1577 else if (flags
& SHORT
)
1578 *ARG (short int *) = (short int) num
.l
;
1579 else if (!(flags
& CHAR
))
1580 *ARG (int *) = (int) num
.l
;
1582 *ARG (signed char *) = (signed char) num
.ul
;
1588 case L_('e'): /* Floating-point numbers. */
1600 /* Check for a sign. */
1601 if (c
== L_('-') || c
== L_('+'))
1603 negative
= c
== L_('-');
1604 if (width
== 0 || inchar () == EOF
)
1605 /* EOF is only an input error before we read any chars. */
1609 #ifdef COMPILE_WSCANF
1612 /* This is no valid number. */
1617 /* Match against the decimal point. At this point
1618 we are taking advantage of the fact that we can
1619 push more than one character back. This is
1620 (almost) never necessary since the decimal point
1621 string hopefully never contains more than one
1623 const char *cmpp
= decimal
;
1624 int avail
= width
> 0 ? width
: INT_MAX
;
1626 while ((unsigned char) *cmpp
== c
&& avail
> 0)
1627 if (*++cmpp
== '\0')
1631 if (inchar () == EOF
)
1638 /* This is no valid number. */
1642 if (cmpp
== decimal
)
1644 c
= (unsigned char) *--cmpp
;
1659 /* Take care for the special arguments "nan" and "inf". */
1660 if (TOLOWER (c
) == L_('n'))
1664 if (width
== 0 || inchar () == EOF
|| TOLOWER (c
) != L_('a'))
1669 if (width
== 0 || inchar () == EOF
|| TOLOWER (c
) != L_('n'))
1677 else if (TOLOWER (c
) == L_('i'))
1679 /* Maybe "inf" or "infinity". */
1681 if (width
== 0 || inchar () == EOF
|| TOLOWER (c
) != L_('n'))
1686 if (width
== 0 || inchar () == EOF
|| TOLOWER (c
) != L_('f'))
1691 /* It is as least "inf". */
1692 if (width
!= 0 && inchar () != EOF
)
1694 if (TOLOWER (c
) == L_('i'))
1698 /* Now we have to read the rest as well. */
1700 if (width
== 0 || inchar () == EOF
1701 || TOLOWER (c
) != L_('n'))
1706 if (width
== 0 || inchar () == EOF
1707 || TOLOWER (c
) != L_('i'))
1712 if (width
== 0 || inchar () == EOF
1713 || TOLOWER (c
) != L_('t'))
1718 if (width
== 0 || inchar () == EOF
1719 || TOLOWER (c
) != L_('y'))
1734 if (width
!= 0 && c
== L_('0'))
1740 if (width
!= 0 && TOLOWER (c
) == L_('x'))
1742 /* It is a number in hexadecimal format. */
1748 /* Grouping is not allowed. */
1756 got_dot
= got_e
= 0;
1761 else if (!got_e
&& is_hexa
&& ISXDIGIT (c
))
1763 else if (got_e
&& wp
[wpsize
- 1] == exp_char
1764 && (c
== L_('-') || c
== L_('+')))
1766 else if (wpsize
> 0 && !got_e
&& TOLOWER (c
) == exp_char
)
1769 got_e
= got_dot
= 1;
1773 #ifdef COMPILE_WSCANF
1774 if (! got_dot
&& c
== decimal
)
1779 else if (thousands
!= L
'\0' && ! got_dot
&& c
== thousands
)
1783 /* The last read character is not part of the number
1789 const char *cmpp
= decimal
;
1790 int avail
= width
> 0 ? width
: INT_MAX
;
1794 while ((unsigned char) *cmpp
== c
&& avail
> 0)
1795 if (*++cmpp
== '\0')
1799 if (inchar () == EOF
)
1807 /* Add all the characters. */
1808 for (cmpp
= decimal
; *cmpp
!= '\0'; ++cmpp
)
1809 ADDW ((unsigned char) *cmpp
);
1816 /* Figure out whether it is a thousands separator.
1817 There is one problem: we possibly read more than
1818 one character. We cannot push them back but since
1819 we know that parts of the `decimal' string matched,
1820 we can compare against it. */
1821 const char *cmp2p
= thousands
;
1823 if (thousands
!= NULL
&& ! got_dot
)
1826 && *cmp2p
== decimal
[cmp2p
- thousands
])
1830 while ((unsigned char) *cmp2p
== c
&& avail
> 0)
1831 if (*++cmp2p
== '\0')
1835 if (inchar () == EOF
)
1842 if (cmp2p
!= NULL
&& *cmp2p
== '\0')
1844 /* Add all the characters. */
1845 for (cmpp
= thousands
; *cmpp
!= '\0'; ++cmpp
)
1846 ADDW ((unsigned char) *cmpp
);
1852 /* The last read character is not part of the number
1863 while (width
!= 0 && inchar () != EOF
);
1865 /* Have we read any character? If we try to read a number
1866 in hexadecimal notation and we have read only the `0x'
1867 prefix or no exponent this is an error. */
1868 if (wpsize
== 0 || (is_hexa
&& (wpsize
== 2 || ! got_e
)))
1872 /* Convert the number. */
1874 if (flags
& LONGDBL
)
1876 long double d
= __strtold_internal (wp
, &tw
, flags
& GROUP
);
1877 if (!(flags
& SUPPRESS
) && tw
!= wp
)
1878 *ARG (long double *) = negative
? -d
: d
;
1880 else if (flags
& LONG
)
1882 double d
= __strtod_internal (wp
, &tw
, flags
& GROUP
);
1883 if (!(flags
& SUPPRESS
) && tw
!= wp
)
1884 *ARG (double *) = negative
? -d
: d
;
1888 float d
= __strtof_internal (wp
, &tw
, flags
& GROUP
);
1889 if (!(flags
& SUPPRESS
) && tw
!= wp
)
1890 *ARG (float *) = negative
? -d
: d
;
1896 if (!(flags
& SUPPRESS
))
1900 case L_('['): /* Character class. */
1902 STRING_ARG (wstr
, wchar_t);
1904 STRING_ARG (str
, char);
1915 /* There is no width given so there is also no limit on the
1916 number of characters we read. Therefore we set width to
1917 a very high value to make the algorithm easier. */
1920 #ifdef COMPILE_WSCANF
1921 /* Find the beginning and the end of the scanlist. We are not
1922 creating a lookup table since it would have to be too large.
1923 Instead we search each time through the string. This is not
1924 a constant lookup time but who uses this feature deserves to
1926 tw
= (wchar_t *) f
; /* Marks the beginning. */
1928 if (*f
== ']' || *f
== '-')
1931 while ((fc
= *f
++) != L
'\0' && fc
!= L
']');
1935 wp
= (wchar_t *) f
- 1;
1937 /* Fill WP with byte flags indexed by character.
1938 We will use this flag map for matching input characters. */
1939 if (wpmax
< UCHAR_MAX
+ 1)
1941 wpmax
= UCHAR_MAX
+ 1;
1942 wp
= (char *) alloca (wpmax
);
1944 memset (wp
, '\0', UCHAR_MAX
+ 1);
1947 if (fc
== ']' || fc
== '-')
1949 /* If ] or - appears before any char in the set, it is not
1950 the terminator or separator, but the first char in the
1956 while ((fc
= *f
++) != '\0' && fc
!= ']')
1957 if (fc
== '-' && *f
!= '\0' && *f
!= ']'
1958 && (unsigned char) f
[-2] <= (unsigned char) *f
)
1960 /* Add all characters from the one before the '-'
1961 up to (but not including) the next format char. */
1962 for (fc
= (unsigned char) f
[-2]; fc
< (unsigned char) *f
; ++fc
)
1966 /* Add the character to the flag map. */
1975 size_t now
= read_in
;
1976 #ifdef COMPILE_WSCANF
1977 if (inchar () == WEOF
)
1984 /* Test whether it's in the scanlist. */
1988 if (runp
[0] == L
'-' && runp
[1] != '\0' && runp
[1] != ']'
1990 && (unsigned int) runp
[-1] <= (unsigned int) runp
[1])
1992 /* Match against all characters in between the
1993 first and last character of the sequence. */
1996 for (wc
= runp
[-1] + 1; wc
< runp
[1]; ++wc
)
2000 if (wc
== runp
[1] && !not_in
)
2002 if (wc
== runp
[1] && not_in
)
2004 /* The current character is not in the
2012 if (*runp
== runp
[1] && !not_in
)
2014 if (*runp
!= runp
[1] && not_in
)
2024 if (!(flags
& SUPPRESS
))
2028 if ((flags
& MALLOC
)
2029 && wstr
== (wchar_t *) *strptr
+ strsize
)
2031 /* Enlarge the buffer. */
2032 wstr
= (wchar_t *) realloc (*strptr
,
2034 * sizeof (wchar_t));
2037 /* Can't allocate that much. Last-ditch
2040 realloc (*strptr
, (strsize
+ 1)
2041 * sizeof (wchar_t));
2044 /* We lose. Oh well. Terminate the string
2045 and stop converting, so at least we don't
2047 ((wchar_t *) (*strptr
))[strsize
- 1] = L
'\0';
2053 *strptr
= (char *) wstr
;
2060 *strptr
= (char *) wstr
;
2067 while (--width
> 0 && inchar () != WEOF
);
2070 char buf
[MB_LEN_MAX
];
2074 if (inchar () == EOF
)
2077 memset (&cstate
, '\0', sizeof (cstate
));
2081 if (wp
[c
] == not_in
)
2083 ungetc_not_eof (c
, s
);
2088 if (!(flags
& SUPPRESS
))
2092 /* Convert it into a wide character. */
2093 n
= __mbrtowc (wstr
, buf
, cnt
, &cstate
);
2095 if (n
== (size_t) -2)
2097 /* Possibly correct character, just not enough
2099 assert (cnt
< MB_CUR_MAX
);
2107 if ((flags
& MALLOC
)
2108 && wstr
== (wchar_t *) *strptr
+ strsize
)
2110 /* Enlarge the buffer. */
2111 wstr
= (wchar_t *) realloc (*strptr
,
2113 * sizeof (wchar_t)));
2116 /* Can't allocate that much. Last-ditch
2119 realloc (*strptr
, ((strsize
+ 1)
2120 * sizeof (wchar_t)));
2123 /* We lose. Oh well. Terminate the
2124 string and stop converting,
2125 so at least we don't skip any input. */
2126 ((wchar_t *) (*strptr
))[strsize
- 1] = L
'\0';
2132 *strptr
= (char *) wstr
;
2139 *strptr
= (char *) wstr
;
2149 while (inchar () != EOF
);
2152 /* We stopped in the middle of recognizing another
2153 character. That's a problem. */
2158 /* We haven't succesfully read any character. */
2161 if (!(flags
& SUPPRESS
))
2165 if ((flags
& MALLOC
)
2166 && wstr
- (wchar_t *) *strptr
!= strsize
)
2168 wchar_t *cp
= (wchar_t *)
2169 realloc (*strptr
, ((wstr
- (wchar_t *) *strptr
)
2170 * sizeof(wchar_t)));
2172 *strptr
= (char *) cp
;
2180 size_t now
= read_in
;
2182 if (inchar () == EOF
)
2185 #ifdef COMPILE_WSCANF
2187 memset (&state
, '\0', sizeof (state
));
2194 /* Test whether it's in the scanlist. */
2198 if (runp
[0] == L
'-' && runp
[1] != '\0' && runp
[1] != ']'
2200 && (unsigned int) runp
[-1] <= (unsigned int) runp
[1])
2202 /* Match against all characters in between the
2203 first and last character of the sequence. */
2206 for (wc
= runp
[-1] + 1; wc
< runp
[1]; ++wc
)
2210 if (wc
== runp
[1] && !not_in
)
2212 if (wc
== runp
[1] && not_in
)
2214 /* The current character is not in the
2222 if (*runp
== runp
[1] && !not_in
)
2224 if (*runp
!= runp
[1] && not_in
)
2234 if (!(flags
& SUPPRESS
))
2236 if ((flags
& MALLOC
)
2237 && str
+ MB_CUR_MAX
>= *strptr
+ strsize
)
2239 /* Enlarge the buffer. */
2240 size_t strleng
= str
- *strptr
;
2243 newstr
= (char *) realloc (*strptr
, 2 * strsize
);
2246 /* Can't allocate that much. Last-ditch
2248 newstr
= (char *) realloc (*strptr
,
2249 strleng
+ MB_CUR_MAX
);
2252 /* We lose. Oh well. Terminate the string
2253 and stop converting, so at least we don't
2255 ((char *) (*strptr
))[strleng
] = '\0';
2262 str
= newstr
+ strleng
;
2263 strsize
= strleng
+ MB_CUR_MAX
;
2269 str
= newstr
+ strleng
;
2275 n
= __wcrtomb (!(flags
& SUPPRESS
) ? str
: NULL
, c
, &state
);
2276 if (n
== (size_t) -1)
2279 assert (n
<= MB_CUR_MAX
);
2282 while (--width
> 0 && inchar () != WEOF
);
2287 if (wp
[c
] == not_in
)
2289 ungetc_not_eof (c
, s
);
2294 if (!(flags
& SUPPRESS
))
2297 if ((flags
& MALLOC
)
2298 && (char *) str
== *strptr
+ strsize
)
2300 /* Enlarge the buffer. */
2301 str
= (char *) realloc (*strptr
, 2 * strsize
);
2304 /* Can't allocate that much. Last-ditch
2306 str
= (char *) realloc (*strptr
, strsize
+ 1);
2309 /* We lose. Oh well. Terminate the
2310 string and stop converting,
2311 so at least we don't skip any input. */
2312 ((char *) (*strptr
))[strsize
- 1] = '\0';
2318 *strptr
= (char *) str
;
2325 *strptr
= (char *) str
;
2332 while (--width
> 0 && inchar () != EOF
);
2336 /* We haven't succesfully read any character. */
2339 if (!(flags
& SUPPRESS
))
2341 #ifdef COMPILE_WSCANF
2342 /* We have to emit the code to get into the initial
2344 char buf
[MB_LEN_MAX
];
2345 size_t n
= __wcrtomb (buf
, L
'\0', &state
);
2346 if (n
> 0 && (flags
& MALLOC
)
2347 && str
+ n
>= *strptr
+ strsize
)
2349 /* Enlarge the buffer. */
2350 size_t strleng
= str
- *strptr
;
2353 newstr
= (char *) realloc (*strptr
, strleng
+ n
+ 1);
2356 /* We lose. Oh well. Terminate the string
2357 and stop converting, so at least we don't
2359 ((char *) (*strptr
))[strleng
] = '\0';
2366 str
= newstr
+ strleng
;
2367 strsize
= strleng
+ n
+ 1;
2371 str
= __mempcpy (str
, buf
, n
);
2375 if ((flags
& MALLOC
) && str
- *strptr
!= strsize
)
2377 char *cp
= (char *) realloc (*strptr
, str
- *strptr
);
2387 case L_('p'): /* Generic pointer. */
2389 /* A PTR must be the same size as a `long int'. */
2390 flags
&= ~(SHORT
|LONGDBL
);
2398 /* If this is an unknown format character punt. */
2403 /* The last thing we saw int the format string was a white space.
2404 Consume the last white spaces. */
2409 while (ISSPACE (c
));
2413 /* Unlock stream. */
2420 # ifdef COMPILE_WSCANF
2422 __vfwscanf (FILE *s
, const wchar_t *format
, va_list argptr
)
2424 return _IO_vfwscanf (s
, format
, argptr
, NULL
);
2428 __vfscanf (FILE *s
, const char *format
, va_list argptr
)
2430 return _IO_vfscanf (s
, format
, argptr
, NULL
);
2435 #ifdef COMPILE_WSCANF
2436 weak_alias (__vfwscanf
, vfwscanf
)
2438 weak_alias (__vfscanf
, vfscanf
)