예제 #1
0
        public override int Parse(string p, int index, TiXmlParsingData data, int encoding)
        {
            value = "";
            TiXmlDocument document = GetDocument();

            if (data != null)
            {
                data.Stamp(p, index, encoding);
                location = data.Cursor();
            }

            const string startTag = "<![CDATA[";
            const string endTag   = "]]>";

            if (cdata || StringEqual(p, index, startTag, false, encoding))
            {
                StringBuilder _value = new StringBuilder();

                cdata = true;

                if (!StringEqual(p, index, startTag, false, encoding))
                {
                    document.SetError(ErrorType.TIXML_ERROR_PARSING_CDATA, p, index, data, encoding);
                    return(INVALID_STRING_INDEX);
                }
                index += startTag.Length;

                // Keep all the white space, ignore the encoding, etc.
                while (index >= 0 && index < p.Length && !StringEqual(p, index, endTag, false, encoding))
                {
                    //value += p[index];
                    _value.Append(p[index]);
                    ++index;
                }

                value = _value.ToString();

                StringBuilder dummy = _value;
                index = ReadText(p, index, dummy, false, endTag, false, encoding);
                return(index);
            }
            else
            {
                StringBuilder _value      = new StringBuilder();
                bool          ignoreWhite = true;

                string end = "<";
                index = ReadText(p, index, _value, ignoreWhite, end, false, encoding);
                value = _value.ToString();
                if (index >= 0)
                {
                    return(index - 1);                          // don't truncate the '<'
                }
                return(INVALID_STRING_INDEX);
            }
        }
예제 #2
0
        public override int Parse(string p, int index, TiXmlParsingData data, int encoding)
        {
            TiXmlDocument document = GetDocument();

            index = SkipWhiteSpace(p, index, encoding);

            if (data != null)
            {
                data.Stamp(p, index, encoding);
                location = data.Cursor();
            }
            //if ( !p || !*p || *p != '<' )
            if (index < 0 || index >= p.Length || p[index] != '<')
            {
                if (document != null)
                {
                    document.SetError(ErrorType.TIXML_ERROR_PARSING_UNKNOWN, p, index, data, encoding);
                }
                return(0);
            }
            ++index;
            value = "";
            StringBuilder _value = new StringBuilder();

            //while ( p && *p && *p != '>' )
            while (index >= 0 && index < p.Length && p[index] != '>')
            {
                //value += p[index];
                _value.Append(p[index]);
                ++index;
            }

            if (index < 0)
            {
                if (document != null)
                {
                    document.SetError(ErrorType.TIXML_ERROR_PARSING_UNKNOWN, null, 0, null, encoding);
                }
                return(INVALID_STRING_INDEX);
            }
            value = _value.ToString();
            if (p[index] == '>')
            {
                return(index + 1);
            }
            return(index);
        }
예제 #3
0
        // [internal use]
        public void SetError(ErrorType err, string pError, int index, TiXmlParsingData data, int encoding)
        {
            // The first error in a chain is more accurate - don't set again!
            if (error)
            {
                return;
            }

            //assert( err > 0 && err < TIXML_ERROR_STRING_COUNT );
            error     = true;
            errorId   = err;
            errorDesc = errorString[(int)errorId];

            errorLocation.Clear();
            if (pError != null && data != null)
            {
                data.Stamp(pError, index, encoding);
                errorLocation = data.Cursor();
            }
        }
예제 #4
0
        /// <summary>
        /// Attribute parsing starts: first letter of the name
        /// </summary>
        /// <returns>the next char after the value end quote</returns>
        public override int Parse(string p, int index, TiXmlParsingData data, int encoding)
        {
            index = SkipWhiteSpace(p, index, encoding);
            if (index < 0 || index >= p.Length)
            {
                return(-1);
            }

            //	int tabsize = 4;
            //	if ( document )
            //		tabsize = document.TabSize();

            if (data != null)
            {
                data.Stamp(p, index, encoding);
                location = data.Cursor();
            }
            // Read the name, the '=' and the value.
            int pErr = index;

            index = ReadName(p, index, ref name, encoding);
            //if ( !p || !*p )
            if (index < 0 || index >= p.Length)
            {
                if (document != null)
                {
                    document.SetError(ErrorType.TIXML_ERROR_READING_ATTRIBUTES, p, pErr, data, encoding);
                }
                return(0);
            }
            index = SkipWhiteSpace(p, index, encoding);
            //if ( !p || !*p || *p != '=' )
            if (index < 0 || index >= p.Length || p[index] != '=')
            {
                if (document != null)
                {
                    document.SetError(ErrorType.TIXML_ERROR_READING_ATTRIBUTES, p, index, data, encoding);
                }
                return(0);
            }

            ++index;                    // skip '='
            index = SkipWhiteSpace(p, index, encoding);
            if (index < 0 || index >= p.Length)
            {
                if (document != null)
                {
                    document.SetError(ErrorType.TIXML_ERROR_READING_ATTRIBUTES, p, index, data, encoding);
                }
                return(0);
            }

            string     end;
            const char SINGLE_QUOTE = '\'';
            const char DOUBLE_QUOTE = '\"';

            StringBuilder _value = new StringBuilder();

            if (p[index] == SINGLE_QUOTE)
            {
                ++index;
                end   = "\'";                           // single quote in string
                index = ReadText(p, index, _value, false, end, false, encoding);
            }
            else if (p[index] == DOUBLE_QUOTE)
            {
                ++index;
                end   = "\"";                           // double quote in string
                index = ReadText(p, index, _value, false, end, false, encoding);
            }
            else
            {
                // All attribute values should be in single or double quotes.
                // But this is such a common error that the parser will try
                // its best, even without them.
                value = "";
                while (index >= 0 && index < p.Length &&                                                        // existence
                       !IsWhiteSpace(p[index]) && p[index] != '\n' && p[index] != '\r' &&                       // whitespace
                       p[index] != '/' && p[index] != '>')                                                      // tag end
                {
                    if (p[index] == SINGLE_QUOTE || p[index] == DOUBLE_QUOTE)
                    {
                        // [ 1451649 ] Attribute values with trailing quotes not handled correctly
                        // We did not have an opening quote but seem to have a
                        // closing one. Give up and throw an error.
                        if (document != null)
                        {
                            document.SetError(ErrorType.TIXML_ERROR_READING_ATTRIBUTES, p, index, data, encoding);
                        }
                        return(INVALID_STRING_INDEX);
                    }
                    //value += p[index];
                    _value.Append(p[index]);
                    ++index;
                }
            }
            value = _value.ToString();
            return(index);
        }
예제 #5
0
        /// <summary>
        /// Parse the given null terminated block of xml data. Passing in an encoding to this
        /// method (either TIXML_ENCODING_LEGACY or TIXML_ENCODING_UTF8 will force TinyXml
        /// to use that encoding, regardless of what TinyXml might otherwise try to detect.
        /// </summary>
        public override int Parse(string p, int index, TiXmlParsingData prevData /* = null*/, int encoding /* = TIXML_DEFAULT_ENCODING*/)
        {
            ClearError();

            // Parse away, at the document level. Since a document
            // contains nothing but other tags, most of what happens
            // here is skipping white space.
            //if ( !p || !*p )
            if (p == null || index < 0 || index >= p.Length)
            {
                SetError(ErrorType.TIXML_ERROR_DOCUMENT_EMPTY, null, 0, null, TiXmlEncoding.TIXML_ENCODING_UNKNOWN);
                return(0);
            }

            // Note that, for a document, this needs to come
            // before the while space skip, so that parsing
            // starts from the pointer we are given.
            location.Clear();
            if (prevData != null)
            {
                location.row = prevData.cursor.row;
                location.col = prevData.cursor.col;
            }
            else
            {
                location.row = 0;
                location.col = 0;
            }
            TiXmlParsingData data = new TiXmlParsingData(p, index, TabSize(), location.row, location.col);

            location = data.Cursor();
#if UNUSED
            if (encoding == TiXmlEncoding.TIXML_ENCODING_UNKNOWN)
            {
                // Check for the Microsoft UTF-8 lead bytes.
                const unsigned char *pU = (const unsigned char *)p;
                if (*(pU + 0) && *(pU + 0) == TIXML_UTF_LEAD_0 &&
                    *(pU + 1) && *(pU + 1) == TIXML_UTF_LEAD_1 &&
                    *(pU + 2) && *(pU + 2) == TIXML_UTF_LEAD_2)
                {
                    encoding        = TIXML_ENCODING_UTF8;
                    useMicrosoftBOM = true;
                }
            }
#endif
            index = SkipWhiteSpace(p, index, encoding);
            //if ( !p )
            if (index < 0)
            {
                SetError(ErrorType.TIXML_ERROR_DOCUMENT_EMPTY, null, 0, null, TiXmlEncoding.TIXML_ENCODING_UNKNOWN);
                return(-1);
            }

            while (index >= 0 && index < p.Length)
            {
                TiXmlNode node = Identify(p, index, encoding);
                if (node != null)
                {
                    index = node.Parse(p, index, data, encoding);
                    LinkEndChild(node);
                }
                else
                {
                    break;
                }

                // Did we get encoding info?
                if (encoding == TiXmlEncoding.TIXML_ENCODING_UNKNOWN && node.ToDeclaration() != null)
                {
                    TiXmlDeclaration dec = node.ToDeclaration();
                    string           enc = dec.Encoding();
                    //assert( enc );

                    if (enc.Length == 0 /**enc == 0 */)
                    {
                        encoding = TiXmlEncoding.TIXML_ENCODING_UTF8;
                    }
                    else if (StringEqual(enc, 0, "UTF-8", true, TiXmlEncoding.TIXML_ENCODING_UNKNOWN))
                    {
                        encoding = TiXmlEncoding.TIXML_ENCODING_UTF8;
                    }
                    else if (StringEqual(enc, 0, "UTF8", true, TiXmlEncoding.TIXML_ENCODING_UNKNOWN))
                    {
                        encoding = TiXmlEncoding.TIXML_ENCODING_UTF8;                           // incorrect, but be nice
                    }
                    else
                    {
                        encoding = TiXmlEncoding.TIXML_ENCODING_LEGACY;
                    }
                }

                index = SkipWhiteSpace(p, index, encoding);
            }

            // Was this empty?
            if (firstChild == null)
            {
                SetError(ErrorType.TIXML_ERROR_DOCUMENT_EMPTY, null, 0, null, encoding);
                return(INVALID_STRING_INDEX);
            }

            // All is well.
            return(index);
        }
예제 #6
0
        /*	Attribtue parsing starts: next char past '<'
         *                                       returns: next char past '>'
         */
        public override int Parse(string p, int index, TiXmlParsingData data, int encoding)
        {
            index = SkipWhiteSpace(p, index, encoding);
            TiXmlDocument document = GetDocument();

            if (p == null || index < 0 || index >= p.Length)
            {
                if (document != null)
                {
                    document.SetError(ErrorType.TIXML_ERROR_PARSING_ELEMENT, null, 0, null, encoding);
                }
                return(0);
            }

            if (data != null)
            {
                data.Stamp(p, index, encoding);
                location = data.Cursor();
            }

            if (p[index] != '<')
            {
                if (document != null)
                {
                    document.SetError(ErrorType.TIXML_ERROR_PARSING_ELEMENT, p, index, data, encoding);
                }
                return(0);
            }

            index = SkipWhiteSpace(p, index + 1, encoding);

            // Read the name.
            int pErr = index;

            index = ReadName(p, index, ref value, encoding);
            if (index < 0 || index >= p.Length)
            {
                if (document != null)
                {
                    document.SetError(ErrorType.TIXML_ERROR_FAILED_TO_READ_ELEMENT_NAME, p, pErr, data, encoding);
                }
                return(INVALID_STRING_INDEX);
            }

            string endTag = "</";

            endTag += value;
            endTag += ">";

            // Check for and read attributes. Also look for an empty
            // tag or an end tag.
            while (index >= 0 && index < p.Length)
            {
                pErr  = index;
                index = SkipWhiteSpace(p, index, encoding);
                if (index < 0 || index >= p.Length)
                {
                    if (document != null)
                    {
                        document.SetError(ErrorType.TIXML_ERROR_READING_ATTRIBUTES, p, pErr, data, encoding);
                    }
                    return(-1);
                }
                if (p[index] == '/')
                {
                    ++index;
                    // Empty tag.
                    if (p[index] != '>')
                    {
                        if (document != null)
                        {
                            document.SetError(ErrorType.TIXML_ERROR_PARSING_EMPTY, p, index, data, encoding);
                        }
                        return(0);
                    }
                    return(index + 1);
                }
                else if (p[index] == '>')
                {
                    // Done with attributes (if there were any.)
                    // Read the value -- which can include other
                    // elements -- read the end tag, and return.
                    ++index;
                    index = ReadValue(p, index, data, encoding); // Note this is an Element method, and will set the error if one happens.
                    if (index < 0 || index >= p.Length)
                    {                                            // We were looking for the end tag, but found nothing.
                                                                 // Fix for [ 1663758 ] Failure to report error on bad XML
                        if (document != null)
                        {
                            document.SetError(ErrorType.TIXML_ERROR_READING_END_TAG, p, index, data, encoding);
                        }
                        return(INVALID_STRING_INDEX);
                    }

                    // We should find the end tag now
                    if (StringEqual(p, index, endTag, false, encoding))
                    {
                        index += endTag.Length;
                        return(index);
                    }
                    else
                    {
                        if (document != null)
                        {
                            document.SetError(ErrorType.TIXML_ERROR_READING_END_TAG, p, index, data, encoding);
                        }
                        return(INVALID_STRING_INDEX);
                    }
                }
                else
                {
                    // Try to read an attribute:
                    TiXmlAttribute attrib = new TiXmlAttribute();
                    if (attrib == null)
                    {
                        if (document != null)
                        {
                            document.SetError(ErrorType.TIXML_ERROR_OUT_OF_MEMORY, p, pErr, data, encoding);
                        }
                        return(-1);
                    }

                    attrib.SetDocument(document);
                    pErr  = index;
                    index = attrib.Parse(p, index, data, encoding);

                    if (index < 0 || index >= p.Length)
                    {
                        if (document != null)
                        {
                            document.SetError(ErrorType.TIXML_ERROR_PARSING_ELEMENT, p, pErr, data, encoding);
                        }
                        //delete attrib;
                        return(INVALID_STRING_INDEX);
                    }

                    // Handle the strange case of double attributes:
                    TiXmlAttribute node = attributeSet.Find(attrib.Name());
                    if (node != null)
                    {
                        node.SetValue(attrib.Value());
                        //delete attrib;
                        return(INVALID_STRING_INDEX);
                    }

                    attributeSet.Add(attrib);
                }
            }
            return(index);
        }
예제 #7
0
        public override int Parse(string p, int index, TiXmlParsingData data, int _encoding)
        {
            index = SkipWhiteSpace(p, index, _encoding);
            // Find the beginning, find the end, and look for
            // the stuff in-between.
            TiXmlDocument document = GetDocument();

            if (index < 0 || index >= p.Length || !StringEqual(p, index, "<?xml", true, _encoding))
            {
                if (document != null)
                {
                    document.SetError(ErrorType.TIXML_ERROR_PARSING_DECLARATION, null, 0, null, _encoding);
                }
                return(INVALID_STRING_INDEX);
            }
            if (data != null)
            {
                data.Stamp(p, index, _encoding);
                location = data.Cursor();
            }
            p += 5;

            version    = "";
            encoding   = "";
            standalone = "";

            while (index >= 0 && index < p.Length)
            {
                if (p[index] == '>')
                {
                    ++index;
                    return(index);
                }

                index = SkipWhiteSpace(p, index, _encoding);
                if (StringEqual(p, index, "version", true, _encoding))
                {
                    TiXmlAttribute attrib = new TiXmlAttribute();
                    index   = attrib.Parse(p, index, data, _encoding);
                    version = attrib.Value();
                }
                else if (StringEqual(p, index, "encoding", true, _encoding))
                {
                    TiXmlAttribute attrib = new TiXmlAttribute();
                    index    = attrib.Parse(p, index, data, _encoding);
                    encoding = attrib.Value();
                }
                else if (StringEqual(p, index, "standalone", true, _encoding))
                {
                    TiXmlAttribute attrib = new TiXmlAttribute();
                    index      = attrib.Parse(p, index, data, _encoding);
                    standalone = attrib.Value();
                }
                else
                {
                    // Read over whatever it is.
                    while (index >= 0 && index < p.Length && p[index] != '>' && !IsWhiteSpace(p[index]))
                    {
                        ++index;
                    }
                }
            }
            return(INVALID_STRING_INDEX);
        }
예제 #8
0
        /*	Attribute parsing starts: at the ! of the !--
         *                                       returns: next char past '>'
         */
        public override int Parse(string p, int index, TiXmlParsingData data, int encoding)
        {
            TiXmlDocument document = GetDocument();

            value = "";

            index = SkipWhiteSpace(p, index, encoding);

            if (data != null)
            {
                data.Stamp(p, index, encoding);
                location = data.Cursor();
            }

            const string startTag = "<!--";
            const string endTag   = "-->";

            if (!StringEqual(p, index, startTag, false, encoding))
            {
                document.SetError(ErrorType.TIXML_ERROR_PARSING_COMMENT, p, index, data, encoding);
                return(INVALID_STRING_INDEX);
            }
            index += startTag.Length;

            // [ 1475201 ] TinyXML parses entities in comments
            // Oops - ReadText doesn't work, because we don't want to parse the entities.
            // p = ReadText( p, &value, false, endTag, false, encoding );
            //
            // from the XML spec:

            /*
             * [Definition: Comments may appear anywhere in a document outside other markup; in addition,
             *                        they may appear within the document type declaration at places allowed by the grammar.
             *                        They are not part of the document's character data; an XML processor MAY, but need not,
             *                        make it possible for an application to retrieve the text of comments. For compatibility,
             *                        the string "--" (double-hyphen) MUST NOT occur within comments.] Parameter entity
             *                        references MUST NOT be recognized within comments.
             *
             *                        An example of a comment:
             *
             *                        <!-- declarations for <head> & <body> -.
             */

            value = "";
            StringBuilder _value = new StringBuilder();

            // Keep all the white space.
            //while (	p && *p && !StringEqual( p, endTag, false, encoding ) )
            while (index >= 0 && index < p.Length && !StringEqual(p, index, endTag, false, encoding))
            {
                _value.Append(p, index, 1);
                ++index;
            }

            if (index >= 0 && index < p.Length)
            {
                index += endTag.Length;
            }
            value = _value.ToString();
            return(index);
        }