1 /* Copyright (C) 1991-1999, 2000 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 (s->_vtable_offset == 0 && _IO_fwide (s, 1) != 1)\
92 # define __strtoll_internal __wcstoll_internal
93 # define __strtoull_internal __wcstoull_internal
94 # define __strtol_internal __wcstol_internal
95 # define __strtoul_internal __wcstoul_internal
96 # define __strtold_internal __wcstold_internal
97 # define __strtod_internal __wcstod_internal
98 # define __strtof_internal __wcstof_internal
100 # define L_(Str) L##Str
101 # define CHAR_T wchar_t
102 # define UCHAR_T unsigned int
103 # define WINT_T wint_t
107 # define ungetc(c, s) ((void) ((int) c == EOF \
109 _IO_sputbackc (s, (unsigned char) c))))
110 # define ungetc_not_eof(c, s) ((void) (--read_in, \
111 _IO_sputbackc (s, (unsigned char) c)))
112 # define inchar() (c == EOF ? EOF \
113 : ((c = _IO_getc_unlocked (s)), \
114 (void) (c != EOF && ++read_in), c))
115 # define MEMCPY(d, s, n) memcpy (d, s, n)
116 # define ISSPACE(Ch) isspace (Ch)
117 # define ISDIGIT(Ch) isdigit (Ch)
118 # define ISXDIGIT(Ch) isxdigit (Ch)
119 # define TOLOWER(Ch) tolower (Ch)
120 # define ORIENT if (_IO_fwide (s, -1) != -1) return EOF
124 # define UCHAR_T unsigned char
128 # define encode_error() do { \
129 if (errp != NULL) *errp |= 4; \
130 _IO_funlockfile (s); \
131 __libc_cleanup_end (0); \
132 __set_errno (EILSEQ); \
135 # define conv_error() do { \
136 if (errp != NULL) *errp |= 2; \
137 _IO_funlockfile (s); \
138 __libc_cleanup_end (0); \
141 # define input_error() do { \
142 _IO_funlockfile (s); \
143 if (errp != NULL) *errp |= 1; \
144 __libc_cleanup_end (0); \
145 return done ?: EOF; \
147 # define memory_error() do { \
148 _IO_funlockfile (s); \
149 __set_errno (ENOMEM); \
150 __libc_cleanup_end (0); \
153 # define ARGCHECK(s, format) \
156 /* Check file argument for consistence. */ \
157 CHECK_FILE (s, EOF); \
158 if (s->_flags & _IO_NO_READS) \
160 __set_errno (EBADF); \
163 else if (format == NULL) \
169 # define LOCK_STREAM(S) \
170 __libc_cleanup_region_start ((void (*) (void *)) &_IO_funlockfile, (S)); \
172 # define UNLOCK_STREAM(S) \
173 _IO_funlockfile (S); \
174 __libc_cleanup_region_end (0)
176 # define ungetc(c, s) ((void) (c != EOF && --read_in), ungetc (c, s))
177 # define ungetc_not_eof(c, s) (--read_in, (ungetc) (c, s))
178 # define inchar() (c == EOF ? EOF \
179 : ((c = getc (s)), (void) (c != EOF && ++read_in), c))
180 # define MEMCPY(d, s, n) memcpy (d, s, n)
181 # define ISSPACE(Ch) isspace (Ch)
182 # define ISDIGIT(Ch) isdigit (Ch)
183 # define ISXDIGIT(Ch) isxdigit (Ch)
184 # define TOLOWER(Ch) tolower (Ch)
188 # define UCHAR_T unsigned char
191 # define encode_error() do { \
193 __set_errno (EILSEQ); \
196 # define conv_error() do { \
200 # define input_error() do { \
202 return done ?: EOF; \
204 # define memory_error() do { \
206 __set_errno (ENOMEM); \
209 # define ARGCHECK(s, format) \
212 /* Check file argument for consistence. */ \
213 if (!__validfp (s) || !s->__mode.__read) \
215 __set_errno (EBADF); \
218 else if (format == NULL) \
220 __set_errno (EINVAL); \
225 /* XXX For now !!! */
226 # define flockfile(S) /* nothing */
227 # define funlockfile(S) /* nothing */
228 # define LOCK_STREAM(S)
229 # define UNLOCK_STREAM(S)
231 # define LOCK_STREAM(S) \
232 __libc_cleanup_region_start (&__funlockfile, (S)); \
234 # define UNLOCK_STREAM(S) \
236 __libc_cleanup_region_end (0)
241 /* Read formatted input from S according to the format string
242 FORMAT, using the argument list in ARG.
243 Return the number of assignments made, or -1 for an input error. */
245 # ifdef COMPILE_WSCANF
247 _IO_vfwscanf (s
, format
, argptr
, errp
)
249 const wchar_t *format
;
254 _IO_vfscanf (s
, format
, argptr
, errp
)
262 __vfscanf (FILE *s
, const char *format
, va_list argptr
)
266 register const CHAR_T
*f
= format
;
267 register UCHAR_T fc
; /* Current character of the format. */
268 register size_t done
= 0; /* Assignments done. */
269 register size_t read_in
= 0; /* Chars read in. */
270 register WINT_T c
= 0; /* Last char read. */
271 register int width
; /* Maximum field width. */
272 register int flags
; /* Modifiers for current format element. */
274 /* Status for reading F-P nums. */
275 char got_dot
, got_e
, negative
;
276 /* If a [...] is a [^...]. */
278 #define exp_char not_in
279 /* Base for integral numbers. */
281 /* Signedness for integral numbers. */
283 #define is_hexa number_signed
284 /* Decimal point character. */
285 #ifdef COMPILE_WSCANF
290 /* The thousands character of the current locale. */
291 #ifdef COMPILE_WSCANF
294 const char *thousands
;
296 /* State for the conversions. */
298 /* Integral holding variables. */
302 unsigned long long int uq
;
304 unsigned long int ul
;
306 /* Character-buffer pointer. */
308 wchar_t *wstr
= NULL
;
309 char **strptr
= NULL
;
311 /* We must not react on white spaces immediately because they can
312 possibly be matched even if in the input stream no character is
313 available anymore. */
315 /* Nonzero if we are reading a pointer. */
318 CHAR_T
*tw
; /* Temporary pointer. */
319 CHAR_T
*wp
= NULL
; /* Workspace. */
320 size_t wpmax
= 0; /* Maximal size of workspace. */
321 size_t wpsize
; /* Currently used bytes in workspace. */
325 if (wpsize == wpmax) \
328 wpmax = (UCHAR_MAX + 1 > 2 * wpmax ? UCHAR_MAX + 1 : 2 * wpmax); \
329 wp = (CHAR_T *) alloca (wpmax * sizeof (wchar_t)); \
331 MEMCPY (wp, old, wpsize); \
333 wp[wpsize++] = (Ch); \
338 __va_copy (arg
, argptr
);
340 arg
= (va_list) argptr
;
347 ARGCHECK (s
, format
);
349 /* Figure out the decimal point character. */
350 #ifdef COMPILE_WSCANF
351 decimal
= _NL_CURRENT_WORD (LC_NUMERIC
, _NL_NUMERIC_DECIMAL_POINT_WC
);
353 decimal
= _NL_CURRENT (LC_NUMERIC
, DECIMAL_POINT
);
355 /* Figure out the thousands separator character. */
356 #ifdef COMPILE_WSCANF
357 thousands
= _NL_CURRENT_WORD (LC_NUMERIC
, _NL_NUMERIC_THOUSANDS_SEP_WC
);
359 thousands
= _NL_CURRENT (LC_NUMERIC
, THOUSANDS_SEP
);
360 if (*thousands
== '\0')
364 /* Lock the stream. */
368 #ifndef COMPILE_WSCANF
369 /* From now on we use `state' to convert the format string. */
370 memset (&state
, '\0', sizeof (state
));
373 /* Run through the format string. */
377 /* Extract the next argument, which is of type TYPE.
378 For a %N$... spec, this is the Nth argument from the beginning;
379 otherwise it is the next argument after the state now in ARG. */
381 # define ARG(type) (argpos == 0 ? va_arg (arg, type) : \
382 ({ unsigned int pos = argpos; \
384 __va_copy (arg, argptr); \
386 (void) va_arg (arg, void *); \
387 va_arg (arg, type); \
391 /* XXX Possible optimization. */
392 # define ARG(type) (argpos == 0 ? va_arg (arg, type) : \
393 ({ va_list arg = (va_list) argptr; \
394 arg = (va_list) ((char *) arg \
396 * __va_rounded_size (void *)); \
397 va_arg (arg, type); \
400 # define ARG(type) (argpos == 0 ? va_arg (arg, type) : \
401 ({ unsigned int pos = argpos; \
402 va_list arg = (va_list) argptr; \
404 (void) va_arg (arg, void *); \
405 va_arg (arg, type); \
410 #ifndef COMPILE_WSCANF
411 if (!isascii ((unsigned char) *f
))
413 /* Non-ASCII, may be a multibyte. */
414 int len
= __mbrlen (f
, strlen (f
), &state
);
422 else if (c
!= (unsigned char) *f
++)
424 ungetc_not_eof (c
, s
);
437 /* Remember to skip spaces. */
444 /* Read a character. */
447 /* Characters other than format specs must just match. */
451 /* We saw white space char as the last character in the format
452 string. Now it's time to skip all leading white space. */
456 if (inchar () == EOF
&& errno
== EINTR
)
470 /* This is the start of the conversion string. */
473 /* Not yet decided whether we read a pointer or not. */
476 /* Initialize state of modifiers. */
479 /* Prepare temporary buffer. */
482 /* Check for a positional parameter specification. */
483 if (ISDIGIT ((UCHAR_T
) *f
))
485 argpos
= (UCHAR_T
) *f
++ - L_('0');
486 while (ISDIGIT ((UCHAR_T
) *f
))
487 argpos
= argpos
* 10 + ((UCHAR_T
) *f
++ - L_('0'));
492 /* Oops; that was actually the field width. */
500 /* Check for the assignment-suppressing, the number grouping flag,
501 and the signal to use the locale's digit representation. */
502 while (*f
== L_('*') || *f
== L_('\'') || *f
== L_('I'))
516 /* We have seen width. */
517 if (ISDIGIT ((UCHAR_T
) *f
))
520 /* Find the maximum field width. */
522 while (ISDIGIT ((UCHAR_T
) *f
))
525 width
+= (UCHAR_T
) *f
++ - L_('0');
531 /* Check for type modifiers. */
535 /* ints are short ints or chars. */
547 /* A double `l' is equivalent to an `L'. */
549 flags
|= LONGDBL
| LONG
;
552 /* ints are long ints. */
557 /* doubles are long doubles, and ints are long long ints. */
558 flags
|= LONGDBL
| LONG
;
561 /* The `a' is used as a flag only if followed by `s', `S' or
563 if (*f
!= L_('s') && *f
!= L_('S') && *f
!= L_('['))
568 /* String conversions (%s, %[) take a `char **'
569 arg and fill it in with a malloc'd pointer. */
573 if (need_longlong
&& sizeof (size_t) > sizeof (unsigned long int))
575 else if (sizeof (size_t) > sizeof (unsigned int))
579 if (need_longlong
&& sizeof (uintmax_t) > sizeof (unsigned long int))
581 else if (sizeof (uintmax_t) > sizeof (unsigned int))
585 if (need_longlong
&& sizeof (ptrdiff_t) > sizeof (long int))
587 else if (sizeof (ptrdiff_t) > sizeof (int))
591 /* Not a recognized modifier. Backup. */
596 /* End of the format string? */
600 /* Find the conversion specifier. */
602 if (skip_space
|| (fc
!= L_('[') && fc
!= L_('c')
603 && fc
!= L_('C') && fc
!= L_('n')))
605 /* Eat whitespace. */
606 int save_errno
= errno
;
609 if (inchar () == EOF
&& errno
== EINTR
)
619 case L_('%'): /* Must match a literal '%'. */
625 ungetc_not_eof (c
, s
);
630 case L_('n'): /* Answer number of assignments done. */
631 /* Corrigendum 1 to ISO C 1990 describes the allowed flags
632 with the 'n' conversion specifier. */
633 if (!(flags
& SUPPRESS
))
635 /* Don't count the read-ahead. */
636 if (need_longlong
&& (flags
& LONGDBL
))
637 *ARG (long long int *) = read_in
;
638 else if (need_long
&& (flags
& LONG
))
639 *ARG (long int *) = read_in
;
640 else if (flags
& SHORT
)
641 *ARG (short int *) = read_in
;
642 else if (!(flags
& CHAR
))
643 *ARG (int *) = read_in
;
645 *ARG (char *) = read_in
;
647 #ifdef NO_BUG_IN_ISO_C_CORRIGENDUM_1
648 /* We have a severe problem here. The ISO C standard
649 contradicts itself in explaining the effect of the %n
650 format in `scanf'. While in ISO C:1990 and the ISO C
651 Amendement 1:1995 the result is described as
653 Execution of a %n directive does not effect the
654 assignment count returned at the completion of
655 execution of the f(w)scanf function.
657 in ISO C Corrigendum 1:1994 the following was added:
660 Add the following fourth example:
663 int d1, d2, n1, n2, i;
664 i = sscanf("123", "%d%n%n%d", &d1, &n1, &n2, &d2);
665 the value 123 is assigned to d1 and the value3 to n1.
666 Because %n can never get an input failure the value
667 of 3 is also assigned to n2. The value of d2 is not
668 affected. The value 3 is assigned to i.
670 We go for now with the historically correct code from ISO C,
671 i.e., we don't count the %n assignments. When it ever
672 should proof to be wrong just remove the #ifdef above. */
678 case L_('c'): /* Match characters. */
679 if ((flags
& LONG
) == 0)
681 if (!(flags
& SUPPRESS
))
695 #ifdef COMPILE_WSCANF
696 /* We have to convert the wide character(s) into multibyte
697 characters and store the result. */
698 memset (&state
, '\0', sizeof (state
));
704 n
= __wcrtomb (!(flags
& SUPPRESS
) ? str
: NULL
, c
, &state
);
705 if (n
== (size_t) -1)
706 /* No valid wide character. */
709 /* Increment the output pointer. Even if we don't
713 while (--width
> 0 && inchar () != EOF
);
715 if (!(flags
& SUPPRESS
))
719 while (--width
> 0 && inchar () != EOF
);
722 while (--width
> 0 && inchar () != EOF
);
725 if (!(flags
& SUPPRESS
))
732 if (!(flags
& SUPPRESS
))
734 wstr
= ARG (wchar_t *);
743 #ifdef COMPILE_WSCANF
744 /* Just store the incoming wide characters. */
745 if (!(flags
& SUPPRESS
))
749 while (--width
> 0 && inchar () != EOF
);
752 while (--width
> 0 && inchar () != EOF
);
755 /* We have to convert the multibyte input sequence to wide
757 char buf
[MB_LEN_MAX
];
760 memset (&cstate
, '\0', sizeof (cstate
));
766 /* This is what we present the mbrtowc function first. */
774 n
= __mbrtowc (!(flags
& SUPPRESS
) ? wstr
: NULL
,
777 if (n
== (size_t) -2)
779 /* Possibly correct character, just not enough
781 assert (cnt
< MB_CUR_MAX
);
783 if (inchar () == EOF
)
793 /* We have a match. */
797 /* Advance the result pointer. */
800 while (--width
> 0 && inchar () != EOF
);
804 if (!(flags
& SUPPRESS
))
809 case L_('s'): /* Read a string. */
812 #define STRING_ARG(Str, Type) \
813 do if (!(flags & SUPPRESS)) \
815 if (flags & MALLOC) \
817 /* The string is to be stored in a malloc'd buffer. */ \
818 strptr = ARG (char **); \
819 if (strptr == NULL) \
821 /* Allocate an initial buffer. */ \
823 *strptr = (char *) malloc (strsize * sizeof (Type)); \
824 Str = (Type *) *strptr; \
827 Str = ARG (Type *); \
831 STRING_ARG (str
, char);
837 #ifdef COMPILE_WSCANF
838 memset (&state
, '\0', sizeof (state
));
845 ungetc_not_eof (c
, s
);
849 #ifdef COMPILE_WSCANF
850 /* This is quite complicated. We have to convert the
851 wide characters into multibyte characters and then
856 if (!(flags
& SUPPRESS
) && (flags
& MALLOC
)
857 && str
+ MB_CUR_MAX
>= *strptr
+ strsize
)
859 /* We have to enlarge the buffer if the `a' flag
861 size_t strleng
= str
- *strptr
;
864 newstr
= (char *) realloc (*strptr
, strsize
* 2);
867 /* Can't allocate that much. Last-ditch
869 newstr
= (char *) realloc (*strptr
,
870 strleng
+ MB_CUR_MAX
);
873 /* We lose. Oh well. Terminate the
874 string and stop converting,
875 so at least we don't skip any input. */
876 ((char *) (*strptr
))[strleng
] = '\0';
883 str
= newstr
+ strleng
;
884 strsize
= strleng
+ MB_CUR_MAX
;
890 str
= newstr
+ strleng
;
895 n
= __wcrtomb (!(flags
& SUPPRESS
) ? str
: NULL
, c
,
897 if (n
== (size_t) -1)
900 assert (n
<= MB_CUR_MAX
);
905 if (!(flags
& SUPPRESS
))
909 && (char *) str
== *strptr
+ strsize
)
911 /* Enlarge the buffer. */
912 str
= (char *) realloc (*strptr
, 2 * strsize
);
915 /* Can't allocate that much. Last-ditch
917 str
= (char *) realloc (*strptr
, strsize
+ 1);
920 /* We lose. Oh well. Terminate the
921 string and stop converting,
922 so at least we don't skip any input. */
923 ((char *) (*strptr
))[strsize
- 1] = '\0';
929 *strptr
= (char *) str
;
936 *strptr
= (char *) str
;
944 while ((width
<= 0 || --width
> 0) && inchar () != EOF
);
946 if (!(flags
& SUPPRESS
))
948 #ifdef COMPILE_WSCANF
949 /* We have to emit the code to get into the initial
951 char buf
[MB_LEN_MAX
];
952 size_t n
= __wcrtomb (buf
, L
'\0', &state
);
953 if (n
> 0 && (flags
& MALLOC
)
954 && str
+ n
>= *strptr
+ strsize
)
956 /* Enlarge the buffer. */
957 size_t strleng
= str
- *strptr
;
960 newstr
= (char *) realloc (*strptr
, strleng
+ n
+ 1);
963 /* We lose. Oh well. Terminate the string
964 and stop converting, so at least we don't
966 ((char *) (*strptr
))[strleng
] = '\0';
973 str
= newstr
+ strleng
;
974 strsize
= strleng
+ n
+ 1;
978 str
= __mempcpy (str
, buf
, n
);
982 if ((flags
& MALLOC
) && str
- *strptr
!= strsize
)
984 char *cp
= (char *) realloc (*strptr
, str
- *strptr
);
997 #ifndef COMPILE_WSCANF
1001 /* Wide character string. */
1002 STRING_ARG (wstr
, wchar_t);
1008 #ifndef COMPILE_WSCANF
1009 memset (&cstate
, '\0', sizeof (cstate
));
1016 ungetc_not_eof (c
, s
);
1020 #ifdef COMPILE_WSCANF
1022 if (!(flags
& SUPPRESS
))
1025 if ((flags
& MALLOC
)
1026 && wstr
== (wchar_t *) *strptr
+ strsize
)
1028 /* Enlarge the buffer. */
1029 wstr
= (wchar_t *) realloc (*strptr
,
1031 * sizeof (wchar_t));
1034 /* Can't allocate that much. Last-ditch
1036 wstr
= (wchar_t *) realloc (*strptr
,
1038 * sizeof (wchar_t));
1041 /* We lose. Oh well. Terminate the string
1042 and stop converting, so at least we don't
1044 ((wchar_t *) (*strptr
))[strsize
- 1] = L
'\0';
1050 *strptr
= (char *) wstr
;
1057 *strptr
= (char *) wstr
;
1065 char buf
[MB_LEN_MAX
];
1075 n
= __mbrtowc (!(flags
& SUPPRESS
) ? wstr
: NULL
,
1078 if (n
== (size_t) -2)
1080 /* Possibly correct character, just not enough
1082 assert (cnt
< MB_CUR_MAX
);
1084 if (inchar () == EOF
)
1094 /* We have a match. */
1098 if (!(flags
& SUPPRESS
) && (flags
& MALLOC
)
1099 && wstr
== (wchar_t *) *strptr
+ strsize
)
1101 /* Enlarge the buffer. */
1102 wstr
= (wchar_t *) realloc (*strptr
,
1104 * sizeof (wchar_t)));
1107 /* Can't allocate that much. Last-ditch effort. */
1108 wstr
= (wchar_t *) realloc (*strptr
,
1110 * sizeof (wchar_t)));
1113 /* We lose. Oh well. Terminate the
1114 string and stop converting, so at
1115 least we don't skip any input. */
1116 ((wchar_t *) (*strptr
))[strsize
- 1] = L
'\0';
1122 *strptr
= (char *) wstr
;
1129 *strptr
= (char *) wstr
;
1137 while ((width
<= 0 || --width
> 0) && inchar () != EOF
);
1139 if (!(flags
& SUPPRESS
))
1143 if ((flags
& MALLOC
) && wstr
- (wchar_t *) *strptr
!= strsize
)
1145 wchar_t *cp
= (wchar_t *) realloc (*strptr
,
1147 - (wchar_t *) *strptr
)
1148 * sizeof(wchar_t)));
1150 *strptr
= (char *) cp
;
1158 case L_('x'): /* Hexadecimal integer. */
1159 case L_('X'): /* Ditto. */
1164 case L_('o'): /* Octal integer. */
1169 case L_('u'): /* Unsigned decimal integer. */
1174 case L_('d'): /* Signed decimal integer. */
1179 case L_('i'): /* Generic number. */
1188 /* Check for a sign. */
1189 if (c
== L_('-') || c
== L_('+'))
1197 /* Look for a leading indication of base. */
1198 if (width
!= 0 && c
== L_('0'))
1206 if (width
!= 0 && TOLOWER (c
) == L_('x'))
1224 if (base
== 10 && (flags
& I18N
) != 0)
1229 #ifdef COMPILE_WSCANF
1230 const wchar_t *wcdigits
[10];
1232 const char *mbdigits
[10];
1237 #ifdef COMPILE_WSCANF
1238 to_level
= _NL_CURRENT_WORD (LC_CTYPE
,
1239 _NL_CTYPE_INDIGITS_WC_LEN
) - 1;
1241 to_level
= _NL_CURRENT_WORD (LC_CTYPE
,
1242 _NL_CTYPE_INDIGITS_MB_LEN
) - 1;
1245 /* Read the number into workspace. */
1246 while (c
!= EOF
&& width
!= 0)
1248 /* In this round we get the pointer to the digit strings
1249 and also perform the first round of comparisons. */
1250 for (n
= 0; n
< 10; ++n
)
1252 /* Get the string for the digits with value N. */
1253 #ifdef COMPILE_WSCANF
1254 wcdigits
[n
] = (const wchar_t *)
1255 _NL_CURRENT (LC_CTYPE
, _NL_CTYPE_INDIGITS0_WC
+ n
);
1256 wcdigits
[n
] += from_level
;
1258 if (c
== *wcdigits
[n
])
1260 to_level
= from_level
;
1264 /* Advance the pointer to the next string. */
1268 int avail
= width
> 0 ? width
: INT_MAX
;
1270 mbdigits
[n
] = _NL_CURRENT (LC_CTYPE
,
1271 _NL_CTYPE_INDIGITS0_MB
+ n
);
1273 for (level
= 0; level
< from_level
; level
++)
1274 mbdigits
[n
] = strchr (mbdigits
[n
], '\0') + 1;
1277 while ((unsigned char) *cmpp
== c
&& avail
> 0)
1279 if (*++cmpp
== '\0')
1283 if ((c
= inchar ()) == EOF
)
1293 to_level
= from_level
;
1297 /* We are pushing all read characters back. */
1298 if (cmpp
> mbdigits
[n
])
1301 while (--cmpp
> mbdigits
[n
])
1302 ungetc_not_eof ((unsigned char) *cmpp
, s
);
1303 c
= (unsigned char) *cmpp
;
1306 /* Advance the pointer to the next string. */
1307 mbdigits
[n
] = strchr (mbdigits
[n
], '\0') + 1;
1313 /* Have not yet found the digit. */
1314 for (level
= from_level
+ 1; level
<= to_level
; ++level
)
1316 /* Search all ten digits of this level. */
1317 for (n
= 0; n
< 10; ++n
)
1319 #ifdef COMPILE_WSCANF
1320 if (c
== *wcdigits
[n
])
1323 /* Advance the pointer to the next string. */
1327 int avail
= width
> 0 ? width
: INT_MAX
;
1330 while ((unsigned char) *cmpp
== c
&& avail
> 0)
1332 if (*++cmpp
== '\0')
1336 if ((c
= inchar ()) == EOF
)
1349 /* We are pushing all read characters back. */
1350 if (cmpp
> mbdigits
[n
])
1353 while (--cmpp
> mbdigits
[n
])
1354 ungetc_not_eof ((unsigned char) *cmpp
, s
);
1355 c
= (unsigned char) *cmpp
;
1358 /* Advance the pointer to the next string. */
1359 mbdigits
[n
] = strchr (mbdigits
[n
], '\0') + 1;
1375 else if ((flags
& GROUP
)
1376 #ifdef COMPILE_WSCANF
1377 && thousands
!= L
'\0'
1379 && thousands
!= NULL
1383 /* Try matching against the thousands separator. */
1384 #ifdef COMPILE_WSCANF
1388 const char *cmpp
= thousands
;
1389 int avail
= width
> 0 ? width
: INT_MAX
;
1391 while ((unsigned char) *cmpp
== c
&& avail
> 0)
1394 if (*++cmpp
== '\0')
1398 if ((c
= inchar ()) == EOF
)
1406 /* We are pushing all read characters back. */
1407 if (cmpp
> thousands
)
1409 wpsize
-= cmpp
- thousands
;
1411 while (--cmpp
> thousands
)
1412 ungetc_not_eof ((unsigned char) *cmpp
, s
);
1413 c
= (unsigned char) *cmpp
;
1421 /* The last thousands character will be added back by
1437 /* Read the number into workspace. */
1438 while (c
!= EOF
&& width
!= 0)
1445 else if (!ISDIGIT (c
) || c
- L_('0') >= base
)
1447 if (base
== 10 && (flags
& GROUP
)
1448 #ifdef COMPILE_WSCANF
1449 && thousands
!= L
'\0'
1451 && thousands
!= NULL
1455 /* Try matching against the thousands separator. */
1456 #ifdef COMPILE_WSCANF
1460 const char *cmpp
= thousands
;
1461 int avail
= width
> 0 ? width
: INT_MAX
;
1463 while ((unsigned char) *cmpp
== c
&& avail
> 0)
1466 if (*++cmpp
== '\0')
1470 if ((c
= inchar ()) == EOF
)
1478 /* We are pushing all read characters back. */
1479 if (cmpp
> thousands
)
1481 wpsize
-= cmpp
- thousands
;
1483 while (--cmpp
> thousands
)
1484 ungetc_not_eof ((unsigned char) *cmpp
, s
);
1485 c
= (unsigned char) *cmpp
;
1493 /* The last thousands character will be added back by
1509 || (wpsize
== 1 && (wp
[0] == L_('+') || wp
[0] == L_('-'))))
1511 /* There was no number. If we are supposed to read a pointer
1512 we must recognize "(nil)" as well. */
1513 if (wpsize
== 0 && read_pointer
&& (width
< 0 || width
>= 0)
1515 && TOLOWER (inchar ()) == L_('n')
1516 && TOLOWER (inchar ()) == L_('i')
1517 && TOLOWER (inchar ()) == L_('l')
1518 && inchar () == L_(')'))
1519 /* We must produce the value of a NULL pointer. A single
1520 '0' digit is enough. */
1524 /* The last read character is not part of the number
1532 /* The just read character is not part of the number anymore. */
1535 /* Convert the number. */
1537 if (need_longlong
&& (flags
& LONGDBL
))
1540 num
.q
= __strtoll_internal (wp
, &tw
, base
, flags
& GROUP
);
1542 num
.uq
= __strtoull_internal (wp
, &tw
, base
, flags
& GROUP
);
1547 num
.l
= __strtol_internal (wp
, &tw
, base
, flags
& GROUP
);
1549 num
.ul
= __strtoul_internal (wp
, &tw
, base
, flags
& GROUP
);
1554 if (!(flags
& SUPPRESS
))
1556 if (! number_signed
)
1558 if (need_longlong
&& (flags
& LONGDBL
))
1559 *ARG (unsigned LONGLONG
int *) = num
.uq
;
1560 else if (need_long
&& (flags
& LONG
))
1561 *ARG (unsigned long int *) = num
.ul
;
1562 else if (flags
& SHORT
)
1563 *ARG (unsigned short int *)
1564 = (unsigned short int) num
.ul
;
1565 else if (!(flags
& CHAR
))
1566 *ARG (unsigned int *) = (unsigned int) num
.ul
;
1568 *ARG (unsigned char *) = (unsigned char) num
.ul
;
1572 if (need_longlong
&& (flags
& LONGDBL
))
1573 *ARG (LONGLONG
int *) = num
.q
;
1574 else if (need_long
&& (flags
& LONG
))
1575 *ARG (long int *) = num
.l
;
1576 else if (flags
& SHORT
)
1577 *ARG (short int *) = (short int) num
.l
;
1578 else if (!(flags
& CHAR
))
1579 *ARG (int *) = (int) num
.l
;
1581 *ARG (signed char *) = (signed char) num
.ul
;
1587 case L_('e'): /* Floating-point numbers. */
1599 /* Check for a sign. */
1600 if (c
== L_('-') || c
== L_('+'))
1602 negative
= c
== L_('-');
1603 if (width
== 0 || inchar () == EOF
)
1604 /* EOF is only an input error before we read any chars. */
1608 #ifdef COMPILE_WSCANF
1611 /* This is no valid number. */
1616 /* Match against the decimal point. At this point
1617 we are taking advantage of the fact that we can
1618 push more than one character back. This is
1619 (almost) never necessary since the decimal point
1620 string hopefully never contains more than one
1622 const char *cmpp
= decimal
;
1623 int avail
= width
> 0 ? width
: INT_MAX
;
1625 while ((unsigned char) *cmpp
== c
&& avail
> 0)
1626 if (*++cmpp
== '\0')
1630 if (inchar () == EOF
)
1637 /* This is no valid number. */
1641 if (cmpp
== decimal
)
1643 c
= (unsigned char) *--cmpp
;
1658 /* Take care for the special arguments "nan" and "inf". */
1659 if (TOLOWER (c
) == L_('n'))
1663 if (width
== 0 || inchar () == EOF
|| TOLOWER (c
) != L_('a'))
1668 if (width
== 0 || inchar () == EOF
|| TOLOWER (c
) != L_('n'))
1676 else if (TOLOWER (c
) == L_('i'))
1678 /* Maybe "inf" or "infinity". */
1680 if (width
== 0 || inchar () == EOF
|| TOLOWER (c
) != L_('n'))
1685 if (width
== 0 || inchar () == EOF
|| TOLOWER (c
) != L_('f'))
1690 /* It is as least "inf". */
1691 if (width
!= 0 && inchar () != EOF
)
1693 if (TOLOWER (c
) == L_('i'))
1697 /* Now we have to read the rest as well. */
1699 if (width
== 0 || inchar () == EOF
1700 || TOLOWER (c
) != L_('n'))
1705 if (width
== 0 || inchar () == EOF
1706 || TOLOWER (c
) != L_('i'))
1711 if (width
== 0 || inchar () == EOF
1712 || TOLOWER (c
) != L_('t'))
1717 if (width
== 0 || inchar () == EOF
1718 || TOLOWER (c
) != L_('y'))
1733 if (width
!= 0 && c
== L_('0'))
1739 if (width
!= 0 && TOLOWER (c
) == L_('x'))
1741 /* It is a number in hexadecimal format. */
1747 /* Grouping is not allowed. */
1755 got_dot
= got_e
= 0;
1760 else if (!got_e
&& is_hexa
&& ISXDIGIT (c
))
1762 else if (got_e
&& wp
[wpsize
- 1] == exp_char
1763 && (c
== L_('-') || c
== L_('+')))
1765 else if (wpsize
> 0 && !got_e
&& TOLOWER (c
) == exp_char
)
1768 got_e
= got_dot
= 1;
1772 #ifdef COMPILE_WSCANF
1773 if (! got_dot
&& c
== decimal
)
1778 else if (thousands
!= L
'\0' && ! got_dot
&& c
== thousands
)
1782 /* The last read character is not part of the number
1788 const char *cmpp
= decimal
;
1789 int avail
= width
> 0 ? width
: INT_MAX
;
1793 while ((unsigned char) *cmpp
== c
&& avail
> 0)
1794 if (*++cmpp
== '\0')
1798 if (inchar () == EOF
)
1806 /* Add all the characters. */
1807 for (cmpp
= decimal
; *cmpp
!= '\0'; ++cmpp
)
1808 ADDW ((unsigned char) *cmpp
);
1815 /* Figure out whether it is a thousands separator.
1816 There is one problem: we possibly read more than
1817 one character. We cannot push them back but since
1818 we know that parts of the `decimal' string matched,
1819 we can compare against it. */
1820 const char *cmp2p
= thousands
;
1822 if (thousands
!= NULL
&& ! got_dot
)
1825 && *cmp2p
== decimal
[cmp2p
- thousands
])
1829 while ((unsigned char) *cmp2p
== c
&& avail
> 0)
1830 if (*++cmp2p
== '\0')
1834 if (inchar () == EOF
)
1841 if (cmp2p
!= NULL
&& *cmp2p
== '\0')
1843 /* Add all the characters. */
1844 for (cmpp
= thousands
; *cmpp
!= '\0'; ++cmpp
)
1845 ADDW ((unsigned char) *cmpp
);
1851 /* The last read character is not part of the number
1862 while (width
!= 0 && inchar () != EOF
);
1864 /* Have we read any character? If we try to read a number
1865 in hexadecimal notation and we have read only the `0x'
1866 prefix or no exponent this is an error. */
1867 if (wpsize
== 0 || (is_hexa
&& (wpsize
== 2 || ! got_e
)))
1871 /* Convert the number. */
1873 if (flags
& LONGDBL
)
1875 long double d
= __strtold_internal (wp
, &tw
, flags
& GROUP
);
1876 if (!(flags
& SUPPRESS
) && tw
!= wp
)
1877 *ARG (long double *) = negative
? -d
: d
;
1879 else if (flags
& LONG
)
1881 double d
= __strtod_internal (wp
, &tw
, flags
& GROUP
);
1882 if (!(flags
& SUPPRESS
) && tw
!= wp
)
1883 *ARG (double *) = negative
? -d
: d
;
1887 float d
= __strtof_internal (wp
, &tw
, flags
& GROUP
);
1888 if (!(flags
& SUPPRESS
) && tw
!= wp
)
1889 *ARG (float *) = negative
? -d
: d
;
1895 if (!(flags
& SUPPRESS
))
1899 case L_('['): /* Character class. */
1901 STRING_ARG (wstr
, wchar_t);
1903 STRING_ARG (str
, char);
1914 /* There is no width given so there is also no limit on the
1915 number of characters we read. Therefore we set width to
1916 a very high value to make the algorithm easier. */
1919 #ifdef COMPILE_WSCANF
1920 /* Find the beginning and the end of the scanlist. We are not
1921 creating a lookup table since it would have to be too large.
1922 Instead we search each time through the string. This is not
1923 a constant lookup time but who uses this feature deserves to
1925 tw
= (wchar_t *) f
; /* Marks the beginning. */
1927 if (*f
== ']' || *f
== '-')
1930 while ((fc
= *f
++) != L
'\0' && fc
!= L
']');
1934 wp
= (wchar_t *) f
- 1;
1936 /* Fill WP with byte flags indexed by character.
1937 We will use this flag map for matching input characters. */
1938 if (wpmax
< UCHAR_MAX
+ 1)
1940 wpmax
= UCHAR_MAX
+ 1;
1941 wp
= (char *) alloca (wpmax
);
1943 memset (wp
, '\0', UCHAR_MAX
+ 1);
1946 if (fc
== ']' || fc
== '-')
1948 /* If ] or - appears before any char in the set, it is not
1949 the terminator or separator, but the first char in the
1955 while ((fc
= *f
++) != '\0' && fc
!= ']')
1956 if (fc
== '-' && *f
!= '\0' && *f
!= ']'
1957 && (unsigned char) f
[-2] <= (unsigned char) *f
)
1959 /* Add all characters from the one before the '-'
1960 up to (but not including) the next format char. */
1961 for (fc
= (unsigned char) f
[-2]; fc
< (unsigned char) *f
; ++fc
)
1965 /* Add the character to the flag map. */
1974 size_t now
= read_in
;
1975 #ifdef COMPILE_WSCANF
1976 if (inchar () == WEOF
)
1983 /* Test whether it's in the scanlist. */
1987 if (runp
[0] == L
'-' && runp
[1] != '\0' && runp
[1] != ']'
1989 && (unsigned int) runp
[-1] <= (unsigned int) runp
[1])
1991 /* Match against all characters in between the
1992 first and last character of the sequence. */
1995 for (wc
= runp
[-1] + 1; wc
< runp
[1]; ++wc
)
1999 if (wc
== runp
[1] && !not_in
)
2001 if (wc
== runp
[1] && not_in
)
2003 /* The current character is not in the
2011 if (*runp
== runp
[1] && !not_in
)
2013 if (*runp
!= runp
[1] && not_in
)
2023 if (!(flags
& SUPPRESS
))
2027 if ((flags
& MALLOC
)
2028 && wstr
== (wchar_t *) *strptr
+ strsize
)
2030 /* Enlarge the buffer. */
2031 wstr
= (wchar_t *) realloc (*strptr
,
2033 * sizeof (wchar_t));
2036 /* Can't allocate that much. Last-ditch
2039 realloc (*strptr
, (strsize
+ 1)
2040 * sizeof (wchar_t));
2043 /* We lose. Oh well. Terminate the string
2044 and stop converting, so at least we don't
2046 ((wchar_t *) (*strptr
))[strsize
- 1] = L
'\0';
2052 *strptr
= (char *) wstr
;
2059 *strptr
= (char *) wstr
;
2066 while (--width
> 0 && inchar () != WEOF
);
2069 char buf
[MB_LEN_MAX
];
2073 if (inchar () == EOF
)
2076 memset (&cstate
, '\0', sizeof (cstate
));
2080 if (wp
[c
] == not_in
)
2082 ungetc_not_eof (c
, s
);
2087 if (!(flags
& SUPPRESS
))
2091 /* Convert it into a wide character. */
2092 n
= __mbrtowc (wstr
, buf
, cnt
, &cstate
);
2094 if (n
== (size_t) -2)
2096 /* Possibly correct character, just not enough
2098 assert (cnt
< MB_CUR_MAX
);
2106 if ((flags
& MALLOC
)
2107 && wstr
== (wchar_t *) *strptr
+ strsize
)
2109 /* Enlarge the buffer. */
2110 wstr
= (wchar_t *) realloc (*strptr
,
2112 * sizeof (wchar_t)));
2115 /* Can't allocate that much. Last-ditch
2118 realloc (*strptr
, ((strsize
+ 1)
2119 * sizeof (wchar_t)));
2122 /* We lose. Oh well. Terminate the
2123 string and stop converting,
2124 so at least we don't skip any input. */
2125 ((wchar_t *) (*strptr
))[strsize
- 1] = L
'\0';
2131 *strptr
= (char *) wstr
;
2138 *strptr
= (char *) wstr
;
2148 while (inchar () != EOF
);
2151 /* We stopped in the middle of recognizing another
2152 character. That's a problem. */
2157 /* We haven't succesfully read any character. */
2160 if (!(flags
& SUPPRESS
))
2164 if ((flags
& MALLOC
)
2165 && wstr
- (wchar_t *) *strptr
!= strsize
)
2167 wchar_t *cp
= (wchar_t *)
2168 realloc (*strptr
, ((wstr
- (wchar_t *) *strptr
)
2169 * sizeof(wchar_t)));
2171 *strptr
= (char *) cp
;
2179 size_t now
= read_in
;
2181 if (inchar () == EOF
)
2184 #ifdef COMPILE_WSCANF
2186 memset (&state
, '\0', sizeof (state
));
2193 /* Test whether it's in the scanlist. */
2197 if (runp
[0] == L
'-' && runp
[1] != '\0' && runp
[1] != ']'
2199 && (unsigned int) runp
[-1] <= (unsigned int) runp
[1])
2201 /* Match against all characters in between the
2202 first and last character of the sequence. */
2205 for (wc
= runp
[-1] + 1; wc
< runp
[1]; ++wc
)
2209 if (wc
== runp
[1] && !not_in
)
2211 if (wc
== runp
[1] && not_in
)
2213 /* The current character is not in the
2221 if (*runp
== runp
[1] && !not_in
)
2223 if (*runp
!= runp
[1] && not_in
)
2233 if (!(flags
& SUPPRESS
))
2235 if ((flags
& MALLOC
)
2236 && str
+ MB_CUR_MAX
>= *strptr
+ strsize
)
2238 /* Enlarge the buffer. */
2239 size_t strleng
= str
- *strptr
;
2242 newstr
= (char *) realloc (*strptr
, 2 * strsize
);
2245 /* Can't allocate that much. Last-ditch
2247 newstr
= (char *) realloc (*strptr
,
2248 strleng
+ MB_CUR_MAX
);
2251 /* We lose. Oh well. Terminate the string
2252 and stop converting, so at least we don't
2254 ((char *) (*strptr
))[strleng
] = '\0';
2261 str
= newstr
+ strleng
;
2262 strsize
= strleng
+ MB_CUR_MAX
;
2268 str
= newstr
+ strleng
;
2274 n
= __wcrtomb (!(flags
& SUPPRESS
) ? str
: NULL
, c
, &state
);
2275 if (n
== (size_t) -1)
2278 assert (n
<= MB_CUR_MAX
);
2281 while (--width
> 0 && inchar () != WEOF
);
2286 if (wp
[c
] == not_in
)
2288 ungetc_not_eof (c
, s
);
2293 if (!(flags
& SUPPRESS
))
2296 if ((flags
& MALLOC
)
2297 && (char *) str
== *strptr
+ strsize
)
2299 /* Enlarge the buffer. */
2300 str
= (char *) realloc (*strptr
, 2 * strsize
);
2303 /* Can't allocate that much. Last-ditch
2305 str
= (char *) realloc (*strptr
, strsize
+ 1);
2308 /* We lose. Oh well. Terminate the
2309 string and stop converting,
2310 so at least we don't skip any input. */
2311 ((char *) (*strptr
))[strsize
- 1] = '\0';
2317 *strptr
= (char *) str
;
2324 *strptr
= (char *) str
;
2331 while (--width
> 0 && inchar () != EOF
);
2335 /* We haven't succesfully read any character. */
2338 if (!(flags
& SUPPRESS
))
2340 #ifdef COMPILE_WSCANF
2341 /* We have to emit the code to get into the initial
2343 char buf
[MB_LEN_MAX
];
2344 size_t n
= __wcrtomb (buf
, L
'\0', &state
);
2345 if (n
> 0 && (flags
& MALLOC
)
2346 && str
+ n
>= *strptr
+ strsize
)
2348 /* Enlarge the buffer. */
2349 size_t strleng
= str
- *strptr
;
2352 newstr
= (char *) realloc (*strptr
, strleng
+ n
+ 1);
2355 /* We lose. Oh well. Terminate the string
2356 and stop converting, so at least we don't
2358 ((char *) (*strptr
))[strleng
] = '\0';
2365 str
= newstr
+ strleng
;
2366 strsize
= strleng
+ n
+ 1;
2370 str
= __mempcpy (str
, buf
, n
);
2374 if ((flags
& MALLOC
) && str
- *strptr
!= strsize
)
2376 char *cp
= (char *) realloc (*strptr
, str
- *strptr
);
2386 case L_('p'): /* Generic pointer. */
2388 /* A PTR must be the same size as a `long int'. */
2389 flags
&= ~(SHORT
|LONGDBL
);
2397 /* If this is an unknown format character punt. */
2402 /* The last thing we saw int the format string was a white space.
2403 Consume the last white spaces. */
2408 while (ISSPACE (c
));
2412 /* Unlock stream. */
2419 # ifdef COMPILE_WSCANF
2421 __vfwscanf (FILE *s
, const wchar_t *format
, va_list argptr
)
2423 return _IO_vfwscanf (s
, format
, argptr
, NULL
);
2427 __vfscanf (FILE *s
, const char *format
, va_list argptr
)
2429 return _IO_vfscanf (s
, format
, argptr
, NULL
);
2434 #ifdef COMPILE_WSCANF
2435 weak_alias (__vfwscanf
, vfwscanf
)
2437 weak_alias (__vfscanf
, vfscanf
)