DontStop() 공개 메소드

Unset the characters where we should stop.
public DontStop ( ) : void
리턴 void
예제 #1
0
        /// <summary>
        ///   Parses a String surrounded with double quotes
        /// </summary>
        private string ParseDoubleQuoted(ParseStream stream)
        {
            System.Text.StringBuilder builder = new System.Text.StringBuilder();

            // Skip '"'
            stream.Next();

            // Stop at "
            stream.StopAt(new char [] { '\"' });

            while (!stream.EOF)
            {
                if (stream.Char == '\n')
                {
                    builder.Append(' ');
                    stream.Next();
                }
                else
                {
                    builder.Append(NextUnescapedChar(stream));
                }
            }

            // Don't stop at "
            stream.DontStop();

            // Skip '"'
            if (stream.Char != '\"')
            {
                throw new ParseException(stream,
                                         "Double quoted string not closed");
            }
            else
            {
                stream.Next(true);
            }

            return(builder.ToString());
        }
        /// <summary> Parse a sequence </summary>
        public Sequence(ParseStream stream)
            : base("tag:yaml.org,2002:seq", NodeType.Sequence)
        {
            // Is this really a sequence?
            if (stream.Char == '-')
            {
                // Parse recursively
                do {
                    // Override the parent's stop chars, never stop
                    stream.StopAt (new char [] { } );

                    // Skip over '-'
                    stream.Next ();

                    // Parse recursively
                    stream.Indent ();
                    AddNode (Parse (stream));
                    stream.UnIndent ();

                    // Re-accept the parent's stop chars
                    stream.DontStop ();
                }
                while ( ! stream.EOF && stream.Char == '-' );
            }
            // Or inline Sequence
            else if (stream.Char == '[')
            {
                // Override the parent's stop chars, never stop
                stream.StopAt (new char [] { });

                // Skip '['
                stream.Next ();

                do {
                    stream.StopAt (new char [] {']', ','});
                    stream.Indent ();
                    AddNode (Parse (stream, false));
                    stream.UnIndent ();
                    stream.DontStop ();

                    // Skip ','
                    if (stream.Char != ']' && stream.Char != ',')
                    {
                        stream.DontStop ();
                        throw new ParseException (stream, "Comma expected in inline sequence");
                    }

                    if (stream.Char == ',')
                    {
                        stream.Next ();
                        stream.SkipSpaces ();
                    }
                }
                while ( ! stream.EOF && stream.Char != ']');

                // Re-accept the parent's stop chars
                stream.DontStop ();

                // Skip ']'
                if (stream.Char == ']')
                    stream.Next (true);
                else
                    throw new ParseException (stream, "Inline sequence not closed");

            }
            // Throw an exception when not
            else
                throw new Exception ("This is not a sequence");
        }
        /// <summary> Parse a mapping </summary>
        public Mapping(ParseStream stream)
            : base("tag:yaml.org,2002:map", NodeType.Mapping)
        {
            // Mapping with eplicit key, (implicit mappings are threaded
            // in Node.cs)
            if (stream.Char == '?')
            {
                // Parse recursively
                do {
                    Node key, val;

                    // Skip over '?'
                    stream.Next ();
                    stream.SkipSpaces ();

                    // Parse recursively. The false param avoids
                    // looking recursively for implicit mappings.
                    stream.StopAt (new char [] {':'});
                    stream.Indent ();
                    key = Parse (stream, false);
                    stream.UnIndent ();
                    stream.DontStop ();

                    // Parse recursively. The false param avoids
                    // looking for implit nodes
                    if (stream.Char == ':')
                    {
                        // Skip over ':'
                        stream.Next ();
                        stream.SkipSpaces ();

                        // Parse recursively
                        stream.Indent ();
                        val = Parse (stream);
                        stream.UnIndent ();
                    }
                    else
                        val = new Null ();

                    AddMappingNode (key, val);

                    // Skip possible newline
                    // NOTE: this can't be done by the drop-newline
                    // method since this is not the end of a block
                    if (stream.Char == '\n')
                        stream.Next ();
                }
                while ( ! stream.EOF && stream.Char == '?');
            }
            // Inline mapping
            else if (stream.Char == '{')
            {
                // Override the parent's stop chars, never stop
                stream.StopAt (new char [] { });

                // Skip '{'
                stream.Next ();

                do {
                    Node key, val;

                    // Skip '?'
                    // (NOTE: it's not obligated to use this '?',
                    // especially because this is an inline mapping)
                    if (stream.Char == '?')
                    {
                        stream.Next ();
                        stream.SkipSpaces ();
                    }

                    // Parse recursively the key
                    stream.StopAt (new char [] {':', ',', '}'});
                    stream.Indent ();
                        key = Parse (stream, false);
                    stream.UnIndent ();
                    stream.DontStop ();

                    // Value
                    if (stream.Char == ':')
                    {
                        // Skip colon
                        stream.Next ();
                        stream.SkipSpaces ();

                        // Parse recursively the value
                        stream.StopAt (new char [] {'}', ','});
                        stream.Indent ();
                            val = Parse (stream, false);
                        stream.UnIndent ();
                        stream.DontStop ();
                    }
                    else
                        val = new Null ();

                    AddMappingNode (key, val);

                    // Skip comma (key sepatator)
                    if (stream.Char != '}' && stream.Char != ',')
                    {
                        stream.DontStop ();
                        throw new ParseException (stream, "Comma expected in inline sequence");
                    }

                    if (stream.Char == ',')
                    {
                        stream.Next ();
                        stream.SkipSpaces ();
                    }
                }
                while ( ! stream.EOF && stream.Char != '}' );

                // Re-accept the parent's stop chars
                stream.DontStop ();

                // Skip '}'
                if (stream.Char == '}')
                    stream.Next ();
                else
                    throw new ParseException (stream, "Inline mapping not closed");
            }
        }
예제 #4
0
        /// <summary> Parse a mapping </summary>
        public Mapping(ParseStream stream) :
            base("tag:yaml.org,2002:map", NodeType.Mapping)
        {
            // Mapping with eplicit key, (implicit mappings are threaded
            // in Node.cs)
            if (stream.Char == '?')
            {
                // Parse recursively
                do
                {
                    Node key, val;

                    // Skip over '?'
                    stream.Next();
                    stream.SkipSpaces();

                    // Parse recursively. The false param avoids
                    // looking recursively for implicit mappings.
                    stream.StopAt(new char [] { ':' });
                    stream.Indent();
                    key = Parse(stream, false);
                    stream.UnIndent();
                    stream.DontStop();

                    // Parse recursively. The false param avoids
                    // looking for implit nodes
                    if (stream.Char == ':')
                    {
                        // Skip over ':'
                        stream.Next();
                        stream.SkipSpaces();

                        // Parse recursively
                        stream.Indent();
                        val = Parse(stream);
                        stream.UnIndent();
                    }
                    else
                    {
                        val = new Null();
                    }

                    AddMappingNode(key, val);

                    // Skip possible newline
                    // NOTE: this can't be done by the drop-newline
                    // method since this is not the end of a block
                    if (stream.Char == '\n')
                    {
                        stream.Next();
                    }
                }while (!stream.EOF && stream.Char == '?');
            }
            // Inline mapping
            else if (stream.Char == '{')
            {
                // Override the parent's stop chars, never stop
                stream.StopAt(new char [] { });

                // Skip '{'
                stream.Next();

                do
                {
                    Node key, val;

                    // Skip '?'
                    // (NOTE: it's not obligated to use this '?',
                    // especially because this is an inline mapping)
                    if (stream.Char == '?')
                    {
                        stream.Next();
                        stream.SkipSpaces();
                    }

                    // Parse recursively the key
                    stream.StopAt(new char [] { ':', ',', '}' });
                    stream.Indent();
                    key = Parse(stream, false);
                    stream.UnIndent();
                    stream.DontStop();

                    // Value
                    if (stream.Char == ':')
                    {
                        // Skip colon
                        stream.Next();
                        stream.SkipSpaces();

                        // Parse recursively the value
                        stream.StopAt(new char [] { '}', ',' });
                        stream.Indent();
                        val = Parse(stream, false);
                        stream.UnIndent();
                        stream.DontStop();
                    }
                    else
                    {
                        val = new Null();
                    }

                    AddMappingNode(key, val);

                    // Skip comma (key sepatator)
                    if (stream.Char != '}' && stream.Char != ',')
                    {
                        stream.DontStop();
                        throw new ParseException(stream, "Comma expected in inline sequence");
                    }

                    if (stream.Char == ',')
                    {
                        stream.Next();
                        stream.SkipSpaces();
                    }
                }while (!stream.EOF && stream.Char != '}');

                // Re-accept the parent's stop chars
                stream.DontStop();

                // Skip '}'
                if (stream.Char == '}')
                {
                    stream.Next();
                }
                else
                {
                    throw new ParseException(stream, "Inline mapping not closed");
                }
            }
        }
예제 #5
0
        /// <summary>
        ///   Reads a character from the stream, unescapes it,
        ///   and moves to the next character.
        /// </summary>
        private char NextUnescapedChar(ParseStream stream)
        {
            char c = stream.Char;

            // If escaped
            if (c == '\\')
            {
                // Never stop, every special character
                // looses its meaning behind a backslash.
                stream.StopAt(new Char [] { });

                stream.Next(true);
                c = stream.Char;

                // ASCII null
                if (c == '0')
                {
                    c = '\0';
                }

                // ASCII bell
                else if (c == 'a')
                {
                    c = (char)0x7;
                }

                // ASCII backspace
                else if (c == 'b')
                {
                    c = (char)0x8;
                }

                // ASCII horizontal tab
                else if (c == 't')
                {
                    c = (char)0x9;
                }

                // ASCII newline
                else if (c == 'n')
                {
                    c = (char)0xA;
                }

                // ASCII vertical tab
                else if (c == 'v')
                {
                    c = (char)0xB;
                }

                // ASCII form feed
                else if (c == 'f')
                {
                    c = (char)0xC;
                }

                // ASCII carriage return
                else if (c == 'r')
                {
                    c = (char)0xD;
                }

                // ASCII escape
                else if (c == 'e')
                {
                    c = (char)0x1D;
                }

                // Unicode next line
                else if (c == 'N')
                {
                    c = (char)0x85;
                }

                // Unicode non breaking space
                else if (c == '_')
                {
                    c = (char)0xA0;
                }

                // TODO larger unicode characters

                // Unicode line separator
                // else if (c == 'L')     c = (char) 0x20282028;

                // 8 bit hexadecimal
                else if (c == 'x')
                {
                    int c_int = (char)0;

                    for (int i = 0; i < 2; i++)
                    {
                        c_int *= 16;

                        stream.Next();
                        char d = stream.Char;

                        if (d >= '0' && d <= '9')
                        {
                            c_int += d - '0';
                        }

                        else if (d >= 'a' && d <= 'f')
                        {
                            c_int += d - 'a';
                        }

                        else if (d >= 'A' && d <= 'F')
                        {
                            c_int += d - 'A';
                        }
                        else
                        {
                            stream.DontStop();
                            throw new ParseException(stream,
                                                     "Invalid escape sequence");
                        }
                    }
                    c = (char)c_int;
                }

                stream.Next(true);

                // Restore last stop settings
                stream.DontStop();
            }
            else
            {
                stream.Next(true);
            }

            return(c);
        }
        /// <summary>
        ///   Parses a String surrounded with double quotes
        /// </summary>
        private string ParseDoubleQuoted(ParseStream stream)
        {
            System.Text.StringBuilder builder = new System.Text.StringBuilder ();

            // Skip '"'
            stream.Next ();

            // Stop at "
            stream.StopAt (new char [] {'\"'} );

            while (! stream.EOF)
            {
                if (stream.Char == '\n')
                {
                    builder.Append (' ');
                    stream.Next ();
                }
                else
                    builder.Append (NextUnescapedChar (stream));
            }

            // Don't stop at "
            stream.DontStop ();

            // Skip '"'
            if (stream.Char != '\"')
                throw new ParseException (stream,
                    "Double quoted string not closed");
            else
                stream.Next (true);

            return builder.ToString();
        }
        /// <summary>
        ///   Reads a character from the stream, unescapes it,
        ///   and moves to the next character.
        /// </summary>
        private char NextUnescapedChar(ParseStream stream)
        {
            char c = stream.Char;

            // If escaped
            if (c == '\\')
            {
                // Never stop, every special character
                // looses its meaning behind a backslash.
                stream.StopAt (new Char [] { });

                stream.Next (true);
                c = stream.Char;

                // ASCII null
                if (c == '0')          c = '\0';

                // ASCII bell
                else if (c == 'a')     c = (char) 0x7;

                // ASCII backspace
                else if (c == 'b')     c = (char) 0x8;

                // ASCII horizontal tab
                else if (c == 't')     c = (char) 0x9;

                // ASCII newline
                else if (c == 'n')     c = (char) 0xA;

                // ASCII vertical tab
                else if (c == 'v')     c = (char) 0xB;

                // ASCII form feed
                else if (c == 'f')     c = (char) 0xC;

                // ASCII carriage return
                else if (c == 'r')     c = (char) 0xD;

                // ASCII escape
                else if (c == 'e')     c = (char) 0x1D;

                // Unicode next line
                else if (c == 'N')     c = (char) 0x85;

                // Unicode non breaking space
                else if (c == '_')     c = (char) 0xA0;

                // TODO larger unicode characters

                // Unicode line separator
                // else if (c == 'L')     c = (char) 0x20282028;

                // 8 bit hexadecimal
                else if (c == 'x')
                {
                    int c_int = (char) 0;

                    for (int i = 0; i < 2; i ++)
                    {
                        c_int *= 16;

                        stream.Next ();
                        char d = stream.Char;

                        if (d >= '0' && d <= '9')
                            c_int += d - '0';

                        else if (d >= 'a' && d <= 'f')
                            c_int += d - 'a';

                        else if (d >= 'A' && d <= 'F')
                            c_int += d - 'A';
                        else
                        {
                            stream.DontStop ();
                            throw new ParseException (stream,
                                "Invalid escape sequence");
                        }
                    }
                    c = (char) c_int;
                }

                stream.Next (true);

                // Restore last stop settings
                stream.DontStop ();
            }
            else
                stream.Next (true);

            return c;
        }
예제 #8
0
        /// <summary> Parse a sequence </summary>
        public Sequence(ParseStream stream) :
            base("tag:yaml.org,2002:seq", NodeType.Sequence)
        {
            // Is this really a sequence?
            if (stream.Char == '-')
            {
                // Parse recursively
                do
                {
                    // Override the parent's stop chars, never stop
                    stream.StopAt(new char [] { });

                    // Skip over '-'
                    stream.Next();

                    // Parse recursively
                    stream.Indent();
                    AddNode(Parse(stream));
                    stream.UnIndent();

                    // Re-accept the parent's stop chars
                    stream.DontStop();
                }while (!stream.EOF && stream.Char == '-');
            }
            // Or inline Sequence
            else if (stream.Char == '[')
            {
                // Override the parent's stop chars, never stop
                stream.StopAt(new char [] { });

                // Skip '['
                stream.Next();

                do
                {
                    stream.StopAt(new char [] { ']', ',' });
                    stream.Indent();
                    AddNode(Parse(stream, false));
                    stream.UnIndent();
                    stream.DontStop();

                    // Skip ','
                    if (stream.Char != ']' && stream.Char != ',')
                    {
                        stream.DontStop();
                        throw new ParseException(stream, "Comma expected in inline sequence");
                    }

                    if (stream.Char == ',')
                    {
                        stream.Next();
                        stream.SkipSpaces();
                    }
                }while (!stream.EOF && stream.Char != ']');

                // Re-accept the parent's stop chars
                stream.DontStop();

                // Skip ']'
                if (stream.Char == ']')
                {
                    stream.Next(true);
                }
                else
                {
                    throw new ParseException(stream, "Inline sequence not closed");
                }
            }
            // Throw an exception when not
            else
            {
                throw new Exception("This is not a sequence");
            }
        }
		/// <summary> Internal parse method </summary>
		/// <param name="parseImplicitMappings">
		///   Avoids ethernal loops while parsing implicit mappings. Implicit mappings are
		///   not rocognized by a leading character. So while trying to parse the key of
		///   something we think that could be a mapping, we're sure that if it is a mapping,
		///   the key of this implicit mapping is not a mapping itself.
		///
		///   NOTE: Implicit mapping still belong to unstable code and require the UNSTABLE and
		///         IMPLICIT_MAPPINGS preprocessor flags.
		/// </param>
		/// <param name="stream"></param>
		protected static Node Parse (ParseStream stream, bool parseImplicitMappings)
		{
			// ----------------
			// Skip Whitespace
			// ----------------
			if (! stream.EOF)
			{
				// Move the firstindentation pointer after the whitespaces of this line
				stream.SkipSpaces ();
				while (stream.Char == '\n' && ! stream.EOF)
				{
					// Skip newline and next whitespaces
					stream.Next ();
					stream.SkipSpaces ();
				}
			}

			// -----------------
			// No remaining chars (Null/empty stream)
			// -----------------
			if (stream.EOF)
				return new Null ();

			// -----------------
			// Explicit type
			// -----------------

#if SUPPORT_EXPLICIT_TYPES
			stream.BuildLookaheadBuffer ();

			char a = '\0', b = '\0';

			a = stream.Char; stream.Next ();
			b = stream.Char; stream.Next ();

			// Starting with !!
			if (a == '!' && b == '!' && ! stream.EOF)
			{
				stream.DestroyLookaheadBuffer ();

				// Read the tagname
				string tag = "";

				while (stream.Char != ' ' && stream.Char != '\n' && ! stream.EOF)
				{
					tag += stream.Char;
					stream.Next ();
				}

				// Skip Whitespace
				if (! stream.EOF)
				{
					stream.SkipSpaces ();
					while (stream.Char == '\n' && ! stream.EOF)
					{
						stream.Next ();
						stream.SkipSpaces ();
					}
				}

				// Parse
				Node n;
				switch (tag)
				{
					// Mappings and sequences
					// NOTE:
					// - sets are mappings without values
					// - Ordered maps are ordered sequence of key: value
					//   pairs without duplicates.
					// - Pairs are ordered sequence of key: value pairs
					//   allowing duplicates.

					// TODO: Create new datatypes for omap and pairs
					//   derived from sequence with a extra duplicate
					//   checking.

					case "seq":       n = new Sequence  (stream); break;
					case "map":       n = new Mapping   (stream); break;
					case "set":       n = new Mapping   (stream); break;
					case "omap":      n = new Sequence  (stream); break;
					case "pairs":     n = new Sequence  (stream); break;

					// Scalars
					//
					// TODO: do we have to move this to Scalar.cs
					// in order to get the following working:
					//
					// !!str "...": "..."
					// !!str "...": "..."

					case "timestamp": n = new Timestamp (stream); break;
					case "binary":    n = new Binary    (stream); break;
					case "null":      n = new Null      (stream); break;
					case "float":     n = new Float     (stream); break;
					case "int":       n = new Integer   (stream); break;
					case "bool":      n = new Boolean   (stream); break;
					case "str":       n = new String    (stream); break;

					// Unknown data type
					default:
						throw  new Exception ("Incorrect tag '!!" + tag + "'");
				}

				return n;
			}
			else
			{
				stream.RewindLookaheadBuffer ();
				stream.DestroyLookaheadBuffer ();
			}
#endif
			// -----------------
			// Sequence
			// -----------------

			if (stream.Char == '-' || stream.Char == '[')
				return new Sequence (stream);

			// -----------------
			// Mapping
			// -----------------

			if (stream.Char == '?' || stream.Char == '{')
				return new Mapping (stream);

			// -----------------
			// Try implicit mapping
			// -----------------

			// This are mappings which are not preceded by a question
			// mark. The keys have to be scalars.

#if (UNSTABLE && SUPPORT_IMPLICIT_MAPPINGS)

			// NOTE: This code can't be included in Mapping.cs
			// because of the way we are using to rewind the buffer.

			Node key, val;

			if (parseImplicitMappings)
			{
				// First Key/value pair

				stream.BuildLookaheadBuffer ();

				stream.StopAt (new char [] {':'});

				// Keys of implicit mappings can't be sequences, or other mappings
				// just look for scalars
				key = Scalar.Parse (stream, false); 
				stream.DontStop ();

Console.WriteLine ("key: " + key);

				// Followed by a colon, so this is a real mapping
				if (stream.Char == ':')
				{
					stream.DestroyLookaheadBuffer ();

					Mapping mapping = new Mapping ();

					// Skip colon and spaces
					stream.Next ();
					stream.SkipSpaces ();

					// Parse the value
Console.Write ("using  buffer: " + stream.UsingBuffer ());
					stream.Indent ();
Console.Write ("using  buffer: " + stream.UsingBuffer ());
//					val = Parse (stream, false);
Console.Write ("<<");
while (!stream.EOF) {Console.Write (stream.Char);stream.Next (true);}
Console.Write (">>");

val = new  String (stream);


Console.Write ("using  buffer: " + stream.UsingBuffer ());
					stream.UnIndent ();
Console.Write ("using  buffer: " + stream.UsingBuffer ());

Console.Write ("<<");
while (!stream.EOF) {Console.Write (stream.Char);stream.Next (true);}
Console.Write (">>");




Console.WriteLine ("val: " + val);
					mapping.AddMappingNode (key, val);

					// Skip possible newline
					// NOTE: this can't be done by the drop-newline
					// method since this is not the end of a block
					while (stream.Char == '\n')
						stream.Next (true);

					// Other key/value pairs
					while (! stream.EOF)
					{
						stream.StopAt (new char [] {':'} );
						stream.Indent ();
						key = Scalar.Parse (stream);
						stream.UnIndent ();
						stream.DontStop ();

Console.WriteLine ("key 2: " + key);
						if (stream.Char == ':')
						{
							// Skip colon and spaces
							stream.Next ();
							stream.SkipSpaces ();

							// Parse the value
							stream.Indent ();
							val = Parse (stream);
							stream.UnIndent ();

Console.WriteLine ("val 2: " + val);
							mapping.AddMappingNode (key, val);
						}
						else // TODO: Is this an error?
						{
							// NOTE: We can't recover from this error,
							// the last buffer has been destroyed, so
							// rewinding is impossible.
							throw new ParseException (stream,
								"Implicit mapping without value node");
						}

						// Skip possible newline
						while (stream.Char == '\n')
							stream.Next ();
					}

					return mapping;
				}

				stream.RewindLookaheadBuffer ();
				stream.DestroyLookaheadBuffer ();
			}

#endif
			// -----------------
			// No known data structure, assume this is a scalar
			// -----------------

			Scalar scalar = Scalar.Parse (stream);

			// Skip trash
			while (! stream.EOF)
				stream.Next ();
		

			return scalar;
		}
예제 #10
0
        /// <summary> Internal parse method </summary>
        /// <param name="parseImplicitMappings">
        ///   Avoids ethernal loops while parsing implicit mappings. Implicit mappings are
        ///   not rocognized by a leading character. So while trying to parse the key of
        ///   something we think that could be a mapping, we're sure that if it is a mapping,
        ///   the key of this implicit mapping is not a mapping itself.
        ///
        ///   NOTE: Implicit mapping still belong to unstable code and require the UNSTABLE and
        ///         IMPLICIT_MAPPINGS preprocessor flags.
        /// </param>
        /// <param name="stream"></param>
        protected static Node Parse(ParseStream stream, bool parseImplicitMappings)
        {
            // ----------------
            // Skip Whitespace
            // ----------------
            if (!stream.EOF)
            {
                // Move the firstindentation pointer after the whitespaces of this line
                stream.SkipSpaces();
                while (stream.Char == '\n' && !stream.EOF)
                {
                    // Skip newline and next whitespaces
                    stream.Next();
                    stream.SkipSpaces();
                }
            }

            // -----------------
            // No remaining chars (Null/empty stream)
            // -----------------
            if (stream.EOF)
            {
                return(new Null());
            }

            // -----------------
            // Explicit type
            // -----------------

#if SUPPORT_EXPLICIT_TYPES
            stream.BuildLookaheadBuffer();

            char a = '\0', b = '\0';

            a = stream.Char; stream.Next();
            b = stream.Char; stream.Next();

            // Starting with !!
            if (a == '!' && b == '!' && !stream.EOF)
            {
                stream.DestroyLookaheadBuffer();

                // Read the tagname
                string tag = "";

                while (stream.Char != ' ' && stream.Char != '\n' && !stream.EOF)
                {
                    tag += stream.Char;
                    stream.Next();
                }

                // Skip Whitespace
                if (!stream.EOF)
                {
                    stream.SkipSpaces();
                    while (stream.Char == '\n' && !stream.EOF)
                    {
                        stream.Next();
                        stream.SkipSpaces();
                    }
                }

                // Parse
                Node n;
                switch (tag)
                {
                // Mappings and sequences
                // NOTE:
                // - sets are mappings without values
                // - Ordered maps are ordered sequence of key: value
                //   pairs without duplicates.
                // - Pairs are ordered sequence of key: value pairs
                //   allowing duplicates.

                // TODO: Create new datatypes for omap and pairs
                //   derived from sequence with a extra duplicate
                //   checking.

                case "seq":       n = new Sequence(stream); break;

                case "map":       n = new Mapping(stream); break;

                case "set":       n = new Mapping(stream); break;

                case "omap":      n = new Sequence(stream); break;

                case "pairs":     n = new Sequence(stream); break;

                // Scalars
                //
                // TODO: do we have to move this to Scalar.cs
                // in order to get the following working:
                //
                // !!str "...": "..."
                // !!str "...": "..."

                case "timestamp": n = new Timestamp(stream); break;

                case "binary":    n = new Binary(stream); break;

                case "null":      n = new Null(stream); break;

                case "float":     n = new Float(stream); break;

                case "int":       n = new Integer(stream); break;

                case "bool":      n = new Boolean(stream); break;

                case "str":       n = new String(stream); break;

                // Unknown data type
                default:
                    throw  new Exception("Incorrect tag '!!" + tag + "'");
                }

                return(n);
            }
            else
            {
                stream.RewindLookaheadBuffer();
                stream.DestroyLookaheadBuffer();
            }
#endif
            // -----------------
            // Sequence
            // -----------------

            if (stream.Char == '-' || stream.Char == '[')
            {
                return(new Sequence(stream));
            }

            // -----------------
            // Mapping
            // -----------------

            if (stream.Char == '?' || stream.Char == '{')
            {
                return(new Mapping(stream));
            }

            // -----------------
            // Try implicit mapping
            // -----------------

            // This are mappings which are not preceded by a question
            // mark. The keys have to be scalars.

#if (UNSTABLE && SUPPORT_IMPLICIT_MAPPINGS)
            // NOTE: This code can't be included in Mapping.cs
            // because of the way we are using to rewind the buffer.

            Node key, val;

            if (parseImplicitMappings)
            {
                // First Key/value pair

                stream.BuildLookaheadBuffer();

                stream.StopAt(new char [] { ':' });

                // Keys of implicit mappings can't be sequences, or other mappings
                // just look for scalars
                key = Scalar.Parse(stream, false);
                stream.DontStop();

                Console.WriteLine("key: " + key);

                // Followed by a colon, so this is a real mapping
                if (stream.Char == ':')
                {
                    stream.DestroyLookaheadBuffer();

                    Mapping mapping = new Mapping();

                    // Skip colon and spaces
                    stream.Next();
                    stream.SkipSpaces();

                    // Parse the value
                    Console.Write("using  buffer: " + stream.UsingBuffer());
                    stream.Indent();
                    Console.Write("using  buffer: " + stream.UsingBuffer());
//					val = Parse (stream, false);
                    Console.Write("<<");
                    while (!stream.EOF)
                    {
                        Console.Write(stream.Char); stream.Next(true);
                    }
                    Console.Write(">>");

                    val = new  String(stream);


                    Console.Write("using  buffer: " + stream.UsingBuffer());
                    stream.UnIndent();
                    Console.Write("using  buffer: " + stream.UsingBuffer());

                    Console.Write("<<");
                    while (!stream.EOF)
                    {
                        Console.Write(stream.Char); stream.Next(true);
                    }
                    Console.Write(">>");



                    Console.WriteLine("val: " + val);
                    mapping.AddMappingNode(key, val);

                    // Skip possible newline
                    // NOTE: this can't be done by the drop-newline
                    // method since this is not the end of a block
                    while (stream.Char == '\n')
                    {
                        stream.Next(true);
                    }

                    // Other key/value pairs
                    while (!stream.EOF)
                    {
                        stream.StopAt(new char [] { ':' });
                        stream.Indent();
                        key = Scalar.Parse(stream);
                        stream.UnIndent();
                        stream.DontStop();

                        Console.WriteLine("key 2: " + key);
                        if (stream.Char == ':')
                        {
                            // Skip colon and spaces
                            stream.Next();
                            stream.SkipSpaces();

                            // Parse the value
                            stream.Indent();
                            val = Parse(stream);
                            stream.UnIndent();

                            Console.WriteLine("val 2: " + val);
                            mapping.AddMappingNode(key, val);
                        }
                        else                         // TODO: Is this an error?
                        {
                            // NOTE: We can't recover from this error,
                            // the last buffer has been destroyed, so
                            // rewinding is impossible.
                            throw new ParseException(stream,
                                                     "Implicit mapping without value node");
                        }

                        // Skip possible newline
                        while (stream.Char == '\n')
                        {
                            stream.Next();
                        }
                    }

                    return(mapping);
                }

                stream.RewindLookaheadBuffer();
                stream.DestroyLookaheadBuffer();
            }
#endif
            // -----------------
            // No known data structure, assume this is a scalar
            // -----------------

            Scalar scalar = Scalar.Parse(stream);

            // Skip trash
            while (!stream.EOF)
            {
                stream.Next();
            }


            return(scalar);
        }