示例#1
0
        /// <summary>
        /// Given that the next character is an ampersand ('&amp;'), attempt to interpret the
        /// following characters as an XML entity.  On success, populate the out parameters
        /// with the low and high UTF-16 surrogates for the character represented by the
        /// entity.
        /// </summary>
        /// <param name="ch">e.g. '&lt;' for &amp;lt;.</param>
        /// <param name="surrogate">e.g. '\uDC00' for &amp;#x10000; (ch == '\uD800').</param>
        /// <returns>True if a valid XML entity was consumed.</returns>
        /// <remarks>
        /// NOTE: Always advances, even on failure.
        /// </remarks>
        public bool TryScanXmlEntity(out char ch, out char surrogate)
        {
            Debug.Assert(this.PeekChar() == '&');

            ch = '&';
            this.AdvanceChar();

            surrogate = InvalidCharacter;

            switch (this.PeekChar())
            {
            case 'l':
                if (AdvanceIfMatches("lt;"))
                {
                    ch = '<';
                    return(true);
                }
                break;

            case 'g':
                if (AdvanceIfMatches("gt;"))
                {
                    ch = '>';
                    return(true);
                }
                break;

            case 'a':
                if (AdvanceIfMatches("amp;"))
                {
                    ch = '&';
                    return(true);
                }
                else if (AdvanceIfMatches("apos;"))
                {
                    ch = '\'';
                    return(true);
                }
                break;

            case 'q':
                if (AdvanceIfMatches("quot;"))
                {
                    ch = '"';
                    return(true);
                }
                break;

            case '#':
            {
                this.AdvanceChar();         //#

                uint uintChar = 0;

                if (AdvanceIfMatches("x"))
                {
                    char digit;
                    while (SyntaxFacts.IsHexDigit(digit = this.PeekChar()))
                    {
                        this.AdvanceChar();

                        // disallow overflow
                        if (uintChar <= 0x7FFFFFF)
                        {
                            uintChar = (uintChar << 4) + (uint)SyntaxFacts.HexValue(digit);
                        }
                        else
                        {
                            return(false);
                        }
                    }
                }
                else
                {
                    char digit;
                    while (SyntaxFacts.IsDecDigit(digit = this.PeekChar()))
                    {
                        this.AdvanceChar();

                        // disallow overflow
                        if (uintChar <= 0x7FFFFFF)
                        {
                            uintChar = (uintChar << 3) + (uintChar << 1) + (uint)SyntaxFacts.DecValue(digit);
                        }
                        else
                        {
                            return(false);
                        }
                    }
                }

                if (AdvanceIfMatches(";"))
                {
                    ch = GetCharsFromUtf32(uintChar, out surrogate);
                    return(true);
                }

                break;
            }
            }

            return(false);
        }
示例#2
0
        private char ScanUnicodeEscape(bool peek, out char surrogateCharacter, out SyntaxDiagnosticInfo info)
        {
            surrogateCharacter = InvalidCharacter;
            info = null;

            int  start     = this.Position;
            char character = this.PeekChar();

            Debug.Assert(character == '\\');
            this.AdvanceChar();

            character = this.PeekChar();
            if (character == 'U')
            {
                uint uintChar = 0;

                this.AdvanceChar();
                if (!SyntaxFacts.IsHexDigit(this.PeekChar()))
                {
                    if (!peek)
                    {
                        info = CreateIllegalEscapeDiagnostic(start);
                    }
                }
                else
                {
                    for (int i = 0; i < 8; i++)
                    {
                        character = this.PeekChar();
                        if (!SyntaxFacts.IsHexDigit(character))
                        {
                            if (!peek)
                            {
                                info = CreateIllegalEscapeDiagnostic(start);
                            }

                            break;
                        }

                        uintChar = (uint)((uintChar << 4) + SyntaxFacts.HexValue(character));
                        this.AdvanceChar();
                    }

                    if (uintChar > 0x0010FFFF)
                    {
                        if (!peek)
                        {
                            info = CreateIllegalEscapeDiagnostic(start);
                        }
                    }
                    else
                    {
                        character = GetCharsFromUtf32(uintChar, out surrogateCharacter);
                    }
                }
            }
            else
            {
                Debug.Assert(character == 'u' || character == 'x');

                int intChar = 0;
                this.AdvanceChar();
                if (!SyntaxFacts.IsHexDigit(this.PeekChar()))
                {
                    if (!peek)
                    {
                        info = CreateIllegalEscapeDiagnostic(start);
                    }
                }
                else
                {
                    for (int i = 0; i < 4; i++)
                    {
                        char ch2 = this.PeekChar();
                        if (!SyntaxFacts.IsHexDigit(ch2))
                        {
                            if (character == 'u')
                            {
                                if (!peek)
                                {
                                    info = CreateIllegalEscapeDiagnostic(start);
                                }
                            }

                            break;
                        }

                        intChar = (intChar << 4) + SyntaxFacts.HexValue(ch2);
                        this.AdvanceChar();
                    }

                    character = (char)intChar;
                }
            }

            return(character);
        }