genericopenlibs/cstdlib/LSTDIO/SSCANF.C
changeset 0 e4d67989cc36
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/genericopenlibs/cstdlib/LSTDIO/SSCANF.C	Tue Feb 02 02:01:42 2010 +0200
@@ -0,0 +1,404 @@
+/* SSCANF.C
+ * 
+ * Portions Copyright (c) 1990-2006 Nokia Corporation and/or its subsidiary(-ies).
+ * All rights reserved.
+ */
+
+/*
+ * 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,
+ * advertising materials, and 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
+	<<scanf>>, <<fscanf>>, <<sscanf>>---scan and format input
+
+INDEX
+	scanf
+INDEX
+	fscanf
+INDEX
+	sscanf
+
+ANSI_SYNOPSIS
+        #include <stdio.h>
+
+        int scanf(const char *<[format]> [, <[arg]>, ...]);
+        int fscanf(FILE *<[fd]>, const char *<[format]> [, <[arg]>, ...]);
+        int sscanf(const char *<[str]>, const char *<[format]> 
+                   [, <[arg]>, ...]);
+
+
+TRAD_SYNOPSIS
+	#include <stdio.h>
+
+	int scanf(<[format]> [, <[arg]>, ...])
+	char *<[format]>;
+
+	int fscanf(<[fd]>, <[format]> [, <[arg]>, ...]);
+	FILE *<[fd]>;
+	char *<[format]>;
+
+	int sscanf(<[str]>, <[format]> [, <[arg]>, ...]);
+	char *<[str]>;
+	char *<[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 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>>, <<l>>, and <<L>> are optional size characters which
+		override the default way that <<scanf>> interprets the
+		data type of the corresponding argument.
+
+
+.Modifier   Type(s)
+.   h       d, i, o, u, x     convert input to short,
+.                             store in short object
+.
+.   h       D, I, O, U, X     no effect
+.           e, f, c, s, n, p
+.
+.   l       d, i, o, u, x     convert input to long,
+.                             store in long object
+.
+.   l       e, f, g           convert input to double
+.                             store in a double object
+.
+.   l       D, I, O, U, X     no effect
+.           c, s, n, p
+.
+.   L       d, i, o, u, x     convert to long double,
+.                             store in long double
+.
+.   L      all others         no effect
+
+
+        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"
+
+static
+int
+eofread (void* cookie,char *buf,int len)
+{
+  	cookie=cookie;
+	buf=buf;
+	len=len;
+	return 0;
+}
+
+/**
+Read formatted data from string.
+Reads data from the buffer specified and stores it
+into the locations given by argument(s).
+Locations pointed by each argument are filled with their corresponding type
+of value requested in the format string.
+
+@param str Buffer containing the string to be parsed for data. 
+@param fmt String that can contain one or more of these items:
+	   Whitespace characters: the function will read and ignore any whitespace
+ 	   characters (this includes blank, newline and tab characters) encountered
+ 	   before the next non-whitespace character. This includes any quantity of
+ 	   whitespace characters (including none). On-whitespace characters (any
+ 	   character not including blank, newline, tab, or any format specifier
+ 	   begining with % character): this cause that the function read and discard
+ 	   any character that match the given non-whitespace character. If this
+ 	   character is not found the function ends returning error.
+ 	   Format specifiers: A sequence of characters begining with '%' indicates
+ 	   that next data has to be readed and stored at the location pointed by its
+ 	   corresponding argument with a given format that is specified following this
+ 	   prototype: %[*][width][modifiers]type
+ 
+@return	On Success, The number of items succesfully read. This count doesn't include any
+ 		ignored fields.
+		On Failure, returns EOF, if an error has occurred before the first assignation
+		could be done and errno may be set.
+*/
+EXPORT_C int sscanf(const char *str, const char *fmt, ...)
+{
+  int ret;
+  va_list ap;
+  FILE f;
+
+  f._data = _REENT2;
+  if (!f._data)
+	return EOF; // Memory for library globals is not allocated (errno not set). 
+  
+  f._flags = __SRD;
+  f._bf._base = f._p = (unsigned char *) str;
+  f._bf._size = f._r = strlen (str);
+  f._read = eofread;
+  f._ub._base = NULL;
+  f._lb._base = NULL;
+  
+  va_start (ap, fmt);
+  ret = __svfscanf (&f, fmt, ap);
+  va_end (ap);
+  return ret;
+}