Welcome to mirror list, hosted at ThFree Co, Russian Federation.

sscanf.c « stdio « libc « newlib - cygwin.com/git/newlib-cygwin.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
blob: 52145fc46c2095be33b6da19a4eace654019c78e (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
/*
 * Copyright (c) 1990 The Regents of the University of California.
 * All rights reserved.
 *
 * Redistribution and use in source and binary forms are permitted
 * provided that the above copyright notice and this paragraph are
 * duplicated in all such forms and that any documentation,
 * and/or other materials related to such
 * distribution and use acknowledge that the software was developed
 * by the University of California, Berkeley.  The name of the
 * University may not be used to endorse or promote products derived
 * from this software without specific prior written permission.
 * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR
 * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
 */

/*
FUNCTION
<<sscanf>>, <<fscanf>>, <<scanf>>---scan and format input

INDEX
	scanf
INDEX
	_scanf_r
INDEX
	fscanf
INDEX
	_fscanf_r
INDEX
	sscanf
INDEX
	_sscanf_r

SYNOPSIS
        #include <stdio.h>

        int scanf(const char *restrict <[format]>, ...);
        int fscanf(FILE *restrict <[fd]>, const char *restrict <[format]>, ...);
        int sscanf(const char *restrict <[str]>, const char *restrict <[format]>, ...);

        int _scanf_r(struct _reent *<[ptr]>, const char *restrict <[format]>, ...);
        int _fscanf_r(struct _reent *<[ptr]>, FILE *restrict <[fd]>, 
                      const char *restrict <[format]>, ...);
        int _sscanf_r(struct _reent *<[ptr]>, const char *restrict <[str]>,
                      const char *restrict <[format]>, ...);

DESCRIPTION
        <<scanf>> scans a series of input fields from standard input,
		one character at a time.  Each field is interpreted according to
		a format specifier passed to <<scanf>> in the format string at
        <<*<[format]>>>.  <<scanf>> stores the interpreted input from
		each field at the address passed to it as the corresponding argument
		following <[format]>.  You must supply the same number of
		format specifiers and address arguments as there are input fields.

        There must be sufficient address arguments for the given format
        specifiers; if not the results are unpredictable and likely
        disasterous.  Excess address arguments are merely ignored.

        <<scanf>> often produces unexpected results if the input diverges from
        an expected pattern. Since the combination of <<gets>> or <<fgets>>
        followed by <<sscanf>> is safe and easy, that is the preferred way
        to be certain that a program is synchronized with input at the end
		of a line.

        <<fscanf>> and <<sscanf>> are identical to <<scanf>>, other than the
        source of input: <<fscanf>> reads from a file, and <<sscanf>>
		from a string.

        The routines <<_scanf_r>>, <<_fscanf_r>>, and <<_sscanf_r>> are reentrant
        versions of <<scanf>>, <<fscanf>>, and <<sscanf>> that take an additional
        first argument pointing to a reentrancy structure.

        The string at <<*<[format]>>> is a character sequence composed
        of zero or more directives. Directives are composed of
        one or more whitespace characters, non-whitespace characters,
        and format specifications.

        Whitespace characters are blank (<< >>), tab (<<\t>>), or
		newline (<<\n>>).
        When <<scanf>> encounters a whitespace character in the format string
        it will read (but not store) all consecutive whitespace characters
        up to the next non-whitespace character in the input.

        Non-whitespace characters are all other ASCII characters except the
        percent sign (<<%>>).  When <<scanf>> encounters a non-whitespace
        character in the format string it will read, but not store
        a matching non-whitespace character.

        Format specifications tell <<scanf>> to read and convert characters
        from the input field into specific types of values, and store then
        in the locations specified by the address arguments.

        Trailing whitespace is left unread unless explicitly
        matched in the format string.

        The format specifiers must begin with a percent sign (<<%>>)
        and have the following form:

.       %[*][<[width]>][<[size]>]<[type]>

        Each format specification begins with the percent character (<<%>>).
        The other fields are:
	O+
		o *

		an optional marker; if present, it suppresses interpretation and
        assignment of this input field.

        o <[width]>

		an optional maximum field width: a decimal integer,
		which controls the maximum number of characters that
		will be read before converting the current input field.  If the
		input field has fewer than <[width]> characters, <<scanf>>
		reads all the characters in the field, and then
		proceeds with the next field and its format specification.

		If a whitespace or a non-convertable character occurs
		before <[width]> character are read, the characters up
		to that character are read, converted, and stored.
		Then <<scanf>> proceeds to the next format specification.

        o <[size]>

		<<h>>, <<j>>, <<l>>, <<L>>, <<t>>, and <<z>> are optional size
		characters which override the default way that <<scanf>>
		interprets the data type of the corresponding argument.

		@multitable @columnfractions 0.18 0.30 0.52
		@headitem
		Modifier
		@tab
		Type(s)
		@tab
		@item
		hh
		@tab
		d, i, o, u, x, n
		@tab
		convert input to char, store in char object
		@item
		h
		@tab
		d, i, o, u, x, n
		@tab
		convert input to short, store in short object
		@item
		h
		@tab
		D, I, O, U, X, e, f, c, s, p
		@tab
		no effect
		@item
		j
		@tab
		d, i, o, u, x, n
		@tab
		convert input to intmax_t, store in intmax_t object
		@item
		j
		@tab
		all others
		@tab
		no effect
		@item
		l
		@tab
		d, i, o, u, x, n
		@tab
		convert input to long, store in long object
		@item
		l
		@tab
		e, f, g
		@tab
		convert input to double, store in a double object
		@item
		l
		@tab
		D, I, O, U, X, c, s, p
		@tab
		no effect
		@item
		ll
		@tab
		d, i, o, u, x, n
		@tab
		convert to long long, store in long long object
		@item
		L
		@tab
		d, i, o, u, x, n
		@tab
		convert to long long, store in long long object
		@item
		L
		@tab
		e, f, g, E, G
		@tab
		convert to long double, store in long double object
		@item
		L
		@tab
		all others
		@tab
		no effect
		@item
		t
		@tab
		d, i, o, u, x, n
		@tab
		convert input to ptrdiff_t, store in ptrdiff_t object
		@item
		t
		@tab
		all others
		@tab
		no effect
		@item
		z
		@tab
		d, i, o, u, x, n
		@tab
		convert input to size_t, store in size_t object
		@item
		z
		@tab
		all others
		@tab
		no effect
		@end multitable

        o <[type]>

		A character to specify what kind of conversion
                <<scanf>> performs.  Here is a table of the conversion
                characters:

		o+
		o %
		No conversion is done; the percent character (<<%>>) is stored.

		o c
		Scans one character.  Corresponding <[arg]>: <<(char *arg)>>.

		o s
		Reads a character string into the array supplied.
		Corresponding <[arg]>: <<(char arg[])>>.

		o [<[pattern]>]
		Reads a non-empty character string into memory
		starting at <[arg]>.  This area must be large
		enough to accept the sequence and a
		terminating null character which will be added
		automatically.  (<[pattern]> is discussed in the paragraph following
		this table). Corresponding <[arg]>: <<(char *arg)>>.

		o d
		Reads a decimal integer into the corresponding <[arg]>: <<(int *arg)>>.

		o D
		Reads a decimal integer into the corresponding
		<[arg]>: <<(long *arg)>>.

		o o
		Reads an octal integer into the corresponding <[arg]>: <<(int *arg)>>.

		o O
		Reads an octal integer into the corresponding <[arg]>: <<(long *arg)>>.

		o u
		Reads an unsigned decimal integer into the corresponding
		<[arg]>: <<(unsigned int *arg)>>.

		o U
		Reads an unsigned decimal integer into the corresponding <[arg]>:
		<<(unsigned long *arg)>>.

		o x,X
		Read a hexadecimal integer into the corresponding <[arg]>:
		<<(int *arg)>>.

		o e, f, g
		Read a floating-point number into the corresponding <[arg]>:
		<<(float *arg)>>.

		o E, F, G
		Read a floating-point number into the corresponding <[arg]>:
		<<(double *arg)>>.

		o i
		Reads a decimal, octal or hexadecimal integer into the
		corresponding <[arg]>: <<(int *arg)>>.

		o I
		Reads a decimal, octal or hexadecimal integer into the
		corresponding <[arg]>: <<(long *arg)>>.

		o n
		Stores the number of characters read in the corresponding
		<[arg]>: <<(int *arg)>>.

		o p
                Stores a scanned pointer.  ANSI C leaves the details
		to each implementation; this implementation treats
		<<%p>> exactly the same as <<%U>>.  Corresponding
		<[arg]>: <<(void **arg)>>.  
                o-

	A <[pattern]> of characters surrounded by square brackets can be used
	instead of the <<s>> type character.  <[pattern]> is a set of
	characters which define a search set of possible characters making up
	the <<scanf>> input field.  If the first character in the brackets is a
	caret (<<^>>), the search set is inverted to include all ASCII characters
	except those between the brackets.  There is also a range facility
	which you can use as a shortcut. <<%[0-9] >> matches all decimal digits.
	The hyphen must not be the first or last character in the set.
	The character prior to the hyphen must be lexically less than the
	character after it.

	Here are some <[pattern]> examples:
		o+
		o %[abcd]
		matches strings containing only <<a>>, <<b>>, <<c>>, and <<d>>.

		o %[^abcd]
		matches strings containing any characters except <<a>>, <<b>>,
		<<c>>, or <<d>>

		o %[A-DW-Z]
		matches strings containing <<A>>, <<B>>, <<C>>, <<D>>, <<W>>,
		<<X>>, <<Y>>, <<Z>>

		o %[z-a]
		matches the characters  <<z>>, <<->>, and <<a>>
		o-

	Floating point numbers (for field types <<e>>, <<f>>, <<g>>, <<E>>,
	<<F>>, <<G>>) must correspond to the following general form:

.		[+/-] ddddd[.]ddd [E|e[+|-]ddd]

	where objects inclosed in square brackets are optional, and <<ddd>>
	represents decimal, octal, or hexadecimal digits.
	O-

RETURNS
        <<scanf>> returns the number of input fields successfully
        scanned, converted and stored; the return value does
        not include scanned fields which were not stored.

        If <<scanf>> attempts to read at end-of-file, the return
        value is <<EOF>>.

        If no fields were stored, the return value is <<0>>.

        <<scanf>> might stop scanning a particular field before
        reaching the normal field end character, or may
        terminate entirely.

        <<scanf>> stops scanning and storing the current field
        and moves to the next input field (if any)
        in any of the following situations:

	O+
	o       The assignment suppressing character (<<*>>) appears
	after the <<%>> in the format specification; the current
	input field is scanned but not stored.

	o       <[width]> characters have been read (<[width]> is a
	width specification, a positive decimal integer).

	o       The next character read cannot be converted
	under the the current format (for example,
	if a <<Z>> is read when the format is decimal).

	o       The next character in the input field does not appear
	in the search set (or does appear in the inverted search set).
	O-

	When <<scanf>> stops scanning the current input field for one of
	these reasons, the next character is considered unread and
	used as the first character of the following input field, or the
	first character in a subsequent read operation on the input.

	<<scanf>> will terminate under the following circumstances:

	O+
	o       The next character in the input field conflicts
	with a corresponding non-whitespace character in the
	format string.

	o       The next character in the input field is <<EOF>>.

	o       The format string has been exhausted.
	O-

	When the format string contains a character sequence that is
	not part of a format specification, the same character
	sequence must appear in the input; <<scanf>> will
	scan but not store the matched characters.  If a
	conflict occurs, the first conflicting character remains in the input
	as if it had never been read.

PORTABILITY
<<scanf>> is ANSI C.

Supporting OS subroutines required: <<close>>, <<fstat>>, <<isatty>>,
<<lseek>>, <<read>>, <<sbrk>>, <<write>>.
*/

#include <_ansi.h>
#include <reent.h>
#include <stdio.h>
#include <string.h>
#include <stdarg.h>
#include "local.h"

#ifndef _REENT_ONLY 

int 
sscanf (const char *__restrict str,
       const char * fmt, ...)
{
  int ret;
  va_list ap;
  FILE f;

  f._flags = __SRD | __SSTR;
  f._flags2 = 0;
  f._bf._base = f._p = (unsigned char *) str;
  f._bf._size = f._r = strlen (str);
  f._read = __seofread;
  f._ub._base = NULL;
  f._lb._base = NULL;
  f._file = -1;  /* No file. */
  va_start (ap, fmt);
  ret = __ssvfscanf_r (_REENT, &f, fmt, ap);
  va_end (ap);
  return ret;
}

#ifdef _NANO_FORMATTED_IO
int
siscanf (const char *, const char *, ...)
       _ATTRIBUTE ((__alias__("sscanf")));
#endif

#endif /* !_REENT_ONLY */

int 
_sscanf_r (struct _reent *ptr,
       const char *__restrict str,
       const char *__restrict fmt, ...)
{
  int ret;
  va_list ap;
  FILE f;

  f._flags = __SRD | __SSTR;
  f._flags2 = 0;
  f._bf._base = f._p = (unsigned char *) str;
  f._bf._size = f._r = strlen (str);
  f._read = __seofread;
  f._ub._base = NULL;
  f._lb._base = NULL;
  f._file = -1;  /* No file. */
  va_start (ap, fmt);
  ret = __ssvfscanf_r (ptr, &f, fmt, ap);
  va_end (ap);
  return ret;
}

#ifdef _NANO_FORMATTED_IO
int
_siscanf_r (struct _reent *, const char *, const char *, ...)
       _ATTRIBUTE ((__alias__("_sscanf_r")));
#endif