AngleSharp by Florian Rappl

<PackageReference Include="AngleSharp" Version="0.5.1" />

 HtmlParser

public sealed class HtmlParser : IParser
Represents the Tree construction as specified in 8.2.5 Tree construction, on the following page: http://www.w3.org/html/wg/drafts/html/master/syntax.html
using AngleSharp.DOM; using AngleSharp.DOM.Html; using AngleSharp.DOM.Mathml; using AngleSharp.DOM.Svg; using System; using System.Collections.Generic; using System.Diagnostics; using System.IO; using System.Text; using System.Threading.Tasks; namespace AngleSharp.Parser.Html { [DebuggerStepThrough] public sealed class HtmlParser : IParser { private HtmlTokenizer tokenizer; private HTMLDocument doc; private HtmlTreeMode insert; private HtmlTreeMode originalInsert; private List<Element> open; private List<Element> formatting; private HTMLFormElement form; private bool frameset; private Node fragmentContext; private bool foster; private int nesting; private bool started; private HTMLScriptElement pendingParsingBlock; private Stack<HtmlTreeMode> templateMode; private Task task; private object sync; public HTMLDocument Result { get { Parse(); return doc; } } public bool IsAsync => task != null; public bool IsFragmentCase => fragmentContext != null; internal Node AdjustedCurrentNode { get { if (fragmentContext == null || open.Count != 1) return CurrentNode; return fragmentContext; } } internal Element CurrentNode { get { if (open.Count <= 0) return null; return open[open.Count - 1]; } } internal HTMLScriptElement PendingParsingBlock { get { return pendingParsingBlock; } set { pendingParsingBlock = value; } } public event EventHandler<ParseErrorEventArgs> ParseError; public HtmlParser(string source, IConfiguration configuration = null) : this(new HTMLDocument { Options = configuration }, new SourceManager(source, configuration.DefaultEncoding())) { } public HtmlParser(Stream stream, IConfiguration configuration = null) : this(new HTMLDocument { Options = configuration }, new SourceManager(stream, configuration.DefaultEncoding())) { } public HtmlParser(HTMLDocument document, string source) : this(document, new SourceManager(source, document.Options.DefaultEncoding())) { } public HtmlParser(HTMLDocument document, Stream stream) : this(document, new SourceManager(stream, document.Options.DefaultEncoding())) { } internal HtmlParser(HTMLDocument document, SourceManager source) { tokenizer = new HtmlTokenizer(source); HtmlTokenizer htmlTokenizer = tokenizer; EventHandler<ParseErrorEventArgs> value = delegate(object s, ParseErrorEventArgs ev) { if (this.ParseError != null) this.ParseError(this, ev); }; htmlTokenizer.ErrorOccurred += value; sync = new object(); started = false; doc = document; open = new List<Element>(); templateMode = new Stack<HtmlTreeMode>(); formatting = new List<Element>(); frameset = true; insert = HtmlTreeMode.Initial; } public Task ParseAsync() { lock (sync) { if (!started) { started = true; task = Task.Factory.StartNew(delegate { Kernel(); }); } else if (task == null) { throw new InvalidOperationException("The parser has already run synchronously."); } return task; } } public void Parse() { bool flag = false; lock (sync) { if (!started) { started = true; flag = true; } } if (flag) Kernel(); } public void SwitchToFragment(Node context) { if (started) throw new InvalidOperationException("Fragment mode has to be activated before running the parser!"); switch (context.NodeName) { case "title": case "textarea": tokenizer.Switch(HtmlParseMode.RCData); break; case "style": case "xmp": case "iframe": case "noembed": case "noframes": tokenizer.Switch(HtmlParseMode.Rawtext); break; case "script": tokenizer.Switch(HtmlParseMode.Script); break; case "noscript": if (doc.Options.IsScripting) tokenizer.Switch(HtmlParseMode.Rawtext); break; case "plaintext": tokenizer.Switch(HtmlParseMode.Plaintext); break; } HTMLHtmlElement hTMLHtmlElement = new HTMLHtmlElement(); doc.AppendChild(hTMLHtmlElement); open.Add(hTMLHtmlElement); if (context is HTMLTemplateElement) templateMode.Push(HtmlTreeMode.InTemplate); Reset(context); fragmentContext = context; tokenizer.AcceptsCharacterData = !AdjustedCurrentNode.IsInHtml; while (!(context is HTMLFormElement)) { context = context.ParentNode; if (context == null) return; } form = (HTMLFormElement)context; } private void Reset(Node context = null) { bool flag = false; int num = open.Count - 1; while (true) { if (num < 0) return; Node node = open[num]; if (num == 0) { flag = true; node = (context ?? node); } switch (node.NodeName) { case "select": insert = HtmlTreeMode.InSelect; return; case "th": case "td": insert = (flag ? HtmlTreeMode.InBody : HtmlTreeMode.InCell); return; case "tr": insert = HtmlTreeMode.InRow; return; case "thead": case "tfoot": case "tbody": insert = HtmlTreeMode.InTableBody; return; case "caption": insert = HtmlTreeMode.InCaption; return; case "colgroup": insert = HtmlTreeMode.InColumnGroup; return; case "table": insert = HtmlTreeMode.InTable; return; case "template": insert = templateMode.Peek(); return; case "head": insert = (flag ? HtmlTreeMode.InBody : HtmlTreeMode.InHead); return; case "body": insert = HtmlTreeMode.InBody; return; case "frameset": insert = HtmlTreeMode.InFrameset; return; case "html": insert = HtmlTreeMode.BeforeHead; return; } if (flag) break; num--; } insert = HtmlTreeMode.InBody; } private void Consume(HtmlToken token) { Node adjustedCurrentNode = AdjustedCurrentNode; if (adjustedCurrentNode == null || adjustedCurrentNode.IsInHtml || token.IsEof || (adjustedCurrentNode.IsHtmlTIP && token.IsHtmlCompatible) || (adjustedCurrentNode.IsMathMLTIP && token.IsMathCompatible) || (adjustedCurrentNode.IsInMathMLSVGReady && token.IsSvg)) Home(token); else Foreign(token); } private void Home(HtmlToken token) { switch (insert) { case HtmlTreeMode.Initial: Initial(token); break; case HtmlTreeMode.BeforeHtml: BeforeHtml(token); break; case HtmlTreeMode.BeforeHead: BeforeHead(token); break; case HtmlTreeMode.InHead: InHead(token); break; case HtmlTreeMode.InHeadNoScript: InHeadNoScript(token); break; case HtmlTreeMode.AfterHead: AfterHead(token); break; case HtmlTreeMode.InBody: InBody(token); break; case HtmlTreeMode.Text: Text(token); break; case HtmlTreeMode.InTable: InTable(token); break; case HtmlTreeMode.InCaption: InCaption(token); break; case HtmlTreeMode.InColumnGroup: InColumnGroup(token); break; case HtmlTreeMode.InTableBody: InTableBody(token); break; case HtmlTreeMode.InRow: InRow(token); break; case HtmlTreeMode.InCell: InCell(token); break; case HtmlTreeMode.InSelect: InSelect(token); break; case HtmlTreeMode.InSelectInTable: InSelectInTable(token); break; case HtmlTreeMode.InTemplate: InTemplate(token); break; case HtmlTreeMode.AfterBody: AfterBody(token); break; case HtmlTreeMode.InFrameset: InFrameset(token); break; case HtmlTreeMode.AfterFrameset: AfterFrameset(token); break; case HtmlTreeMode.AfterAfterBody: AfterAfterBody(token); break; case HtmlTreeMode.AfterAfterFrameset: AfterAfterFrameset(token); break; } } private void Initial(HtmlToken token) { if (token.Type == HtmlTokenType.DOCTYPE) { HtmlDoctypeToken htmlDoctypeToken = (HtmlDoctypeToken)token; if (!htmlDoctypeToken.IsValid) RaiseErrorOccurred(ErrorCode.DoctypeInvalid); AddDoctype(htmlDoctypeToken); if (htmlDoctypeToken.IsFullQuirks) doc.QuirksMode = QuirksMode.On; else if (htmlDoctypeToken.IsLimitedQuirks) { doc.QuirksMode = QuirksMode.Limited; } insert = HtmlTreeMode.BeforeHtml; } else { if (token.Type == HtmlTokenType.Character) { HtmlCharacterToken htmlCharacterToken = (HtmlCharacterToken)token; htmlCharacterToken.TrimStart(); if (htmlCharacterToken.IsEmpty) return; } else if (token.Type == HtmlTokenType.Comment) { AddComment(doc, token); return; } if (!doc.Options.IsEmbedded) { RaiseErrorOccurred(ErrorCode.DoctypeMissing); doc.QuirksMode = QuirksMode.On; } insert = HtmlTreeMode.BeforeHtml; BeforeHtml(token); } } private void BeforeHtml(HtmlToken token) { if (token.IsStartTag("html")) { AddRoot(token.AsTag()); insert = HtmlTreeMode.BeforeHead; } else if (token.Type == HtmlTokenType.DOCTYPE) { RaiseErrorOccurred(ErrorCode.DoctypeTagInappropriate); } else { if (token.Type == HtmlTokenType.Character) { HtmlCharacterToken htmlCharacterToken = (HtmlCharacterToken)token; htmlCharacterToken.TrimStart(); if (htmlCharacterToken.IsEmpty) return; } else { if (token.Type == HtmlTokenType.Comment) { AddComment(doc, token); return; } if (token.IsEndTagInv("html", "body", "br", "head")) { RaiseErrorOccurred(ErrorCode.TagCannotEndHere); return; } } BeforeHtml(HtmlToken.OpenTag("html")); BeforeHead(token); } } private void BeforeHead(HtmlToken token) { if (token.Type == HtmlTokenType.Character) { HtmlCharacterToken htmlCharacterToken = (HtmlCharacterToken)token; htmlCharacterToken.TrimStart(); if (htmlCharacterToken.IsEmpty) return; } else { if (token.Type == HtmlTokenType.StartTag && ((HtmlTagToken)token).Name == "html") { InBody(token); return; } if (token.Type == HtmlTokenType.StartTag && ((HtmlTagToken)token).Name == "head") { AddElement(new HTMLHeadElement(), token.AsTag(), false); insert = HtmlTreeMode.InHead; return; } if (token.Type == HtmlTokenType.Comment) { AddComment(token); return; } if (token.Type == HtmlTokenType.DOCTYPE) { RaiseErrorOccurred(ErrorCode.DoctypeTagInappropriate); return; } if (token.IsEndTagInv("html", "body", "br", "head")) { RaiseErrorOccurred(ErrorCode.TagCannotEndHere); return; } } BeforeHead(HtmlToken.OpenTag("head")); InHead(token); } private void InHead(HtmlToken token) { if (token.Type == HtmlTokenType.Character) { HtmlCharacterToken htmlCharacterToken = (HtmlCharacterToken)token; string text = htmlCharacterToken.TrimStart(); AddCharacters(text); if (htmlCharacterToken.IsEmpty) return; } else { if (token.Type == HtmlTokenType.Comment) { AddComment(token); return; } if (token.Type == HtmlTokenType.DOCTYPE) { RaiseErrorOccurred(ErrorCode.DoctypeTagInappropriate); return; } if (token.IsStartTag("html")) { InBody(token); return; } if (token.IsStartTag("meta")) { HTMLMetaElement hTMLMetaElement = new HTMLMetaElement(); AddElement(hTMLMetaElement, token.AsTag(), true); CloseCurrentNode(); string attribute = hTMLMetaElement.GetAttribute(AttributeNames.Charset); if (attribute != null && DocumentEncoding.IsSupported(attribute)) SetCharset(attribute); else { attribute = hTMLMetaElement.GetAttribute(AttributeNames.HttpEquiv); if (attribute != null && attribute.Equals("Content-Type", StringComparison.OrdinalIgnoreCase)) { attribute = (hTMLMetaElement.GetAttribute(AttributeNames.Content) ?? string.Empty); attribute = DocumentEncoding.Extract(attribute); if (DocumentEncoding.IsSupported(attribute)) SetCharset(attribute); } } return; } if (token.IsStartTag("link", "base", "basefont", "bgsound")) { AddElement(token.AsTag(), true); CloseCurrentNode(); return; } if (token.IsStartTag("title")) { RCDataAlgorithm(token.AsTag()); return; } if (token.IsStartTag("style", "noframes") || (doc.Options.IsScripting && token.IsStartTag("noscript"))) { RawtextAlgorithm(token.AsTag()); return; } if (token.IsStartTag("noscript")) { AddElement(token.AsTag(), false); insert = HtmlTreeMode.InHeadNoScript; return; } if (token.IsStartTag("script")) { AddElement(token.AsTag(), false); tokenizer.Switch(HtmlParseMode.Script); originalInsert = insert; insert = HtmlTreeMode.Text; return; } if (token.IsEndTag("head")) { CloseCurrentNode(); insert = HtmlTreeMode.AfterHead; return; } if (token.IsStartTag("head")) { RaiseErrorOccurred(ErrorCode.HeadTagMisplaced); return; } if (token.IsTag("template")) { if (token.Type == HtmlTokenType.StartTag) { HTMLTemplateElement element = new HTMLTemplateElement(); AddElement(element, token.AsTag(), false); AddScopeMarker(); frameset = false; insert = HtmlTreeMode.InTemplate; templateMode.Push(HtmlTreeMode.InTemplate); } else if (TagCurrentlyOpen("template")) { GenerateImpliedEndTags(); if (!(CurrentNode is HTMLTemplateElement)) RaiseErrorOccurred(ErrorCode.TagClosingMismatch); CloseTemplate(); } else { RaiseErrorOccurred(ErrorCode.TagInappropriate); } return; } if (token.IsEndTagInv("html", "body", "br")) { RaiseErrorOccurred(ErrorCode.TagCannotEndHere); return; } } CloseCurrentNode(); insert = HtmlTreeMode.AfterHead; AfterHead(token); } private void InHeadNoScript(HtmlToken token) { if (token.Type == HtmlTokenType.Character) { HtmlCharacterToken htmlCharacterToken = (HtmlCharacterToken)token; string text = htmlCharacterToken.TrimStart(); AddCharacters(text); if (htmlCharacterToken.IsEmpty) return; } else { if (token.Type == HtmlTokenType.Comment) { InHead(token); return; } if (token.IsEndTag("noscript")) { CloseCurrentNode(); insert = HtmlTreeMode.InHead; return; } if (token.IsStartTag("style", "link", "basefont", "meta", "noframes", "bgsound")) { InHead(token); return; } if (token.IsStartTag("html")) { InBody(token); return; } if (token.IsStartTag("head", "noscript")) { RaiseErrorOccurred(ErrorCode.TagInappropriate); return; } if (token.IsEndTagInv("br")) { RaiseErrorOccurred(ErrorCode.TagCannotEndHere); return; } if (token.Type == HtmlTokenType.DOCTYPE) { RaiseErrorOccurred(ErrorCode.DoctypeTagInappropriate); return; } } RaiseErrorOccurred(ErrorCode.TokenNotPossible); CloseCurrentNode(); insert = HtmlTreeMode.InHead; InHead(token); } private void AfterHead(HtmlToken token) { if (token.Type == HtmlTokenType.Character) { HtmlCharacterToken htmlCharacterToken = (HtmlCharacterToken)token; string text = htmlCharacterToken.TrimStart(); AddCharacters(text); if (htmlCharacterToken.IsEmpty) return; } else { if (token.Type == HtmlTokenType.Comment) { AddComment(token); return; } if (token.Type == HtmlTokenType.DOCTYPE) { RaiseErrorOccurred(ErrorCode.DoctypeTagInappropriate); return; } if (token.IsStartTag("html")) { InBody(token); return; } if (token.IsStartTag("body")) { AfterHeadStartTagBody((HtmlTagToken)token); return; } if (token.IsStartTag("frameset")) { HTMLFrameSetElement element = new HTMLFrameSetElement(); AddElement(element, token.AsTag(), false); insert = HtmlTreeMode.InFrameset; return; } if (token.IsStartTag("base", "basefont", "bgsound", "link", "meta", "noframes", "script", "style", "title")) { RaiseErrorOccurred(ErrorCode.TagMustBeInHead); int count = open.Count; open.Add(doc.Head); InHead(token); open.RemoveAt(count); return; } if (token.IsStartTag("head")) { RaiseErrorOccurred(ErrorCode.HeadTagMisplaced); return; } if (token.IsEndTagInv("html", "body", "br")) { RaiseErrorOccurred(ErrorCode.TagCannotEndHere); return; } } AfterHeadStartTagBody(HtmlToken.OpenTag("body")); frameset = true; Home(token); } private void InBody(HtmlToken token) { if (token.Type == HtmlTokenType.Character) { HtmlCharacterToken htmlCharacterToken = (HtmlCharacterToken)token; ReconstructFormatting(); AddCharacters(htmlCharacterToken.Data); if (htmlCharacterToken.HasContent) frameset = false; } else if (token.Type == HtmlTokenType.Comment) { AddComment(token); } else if (token.Type == HtmlTokenType.DOCTYPE) { RaiseErrorOccurred(ErrorCode.DoctypeTagInappropriate); } else if (token.Type == HtmlTokenType.StartTag) { HtmlTagToken htmlTagToken = (HtmlTagToken)token; switch (htmlTagToken.Name) { case "html": RaiseErrorOccurred(ErrorCode.HtmlTagMisplaced); if (templateMode.Count == 0) AppendAttributes(htmlTagToken, open[0]); break; case "base": case "basefont": case "bgsound": case "link": case "menuitem": case "meta": case "noframes": case "script": case "style": case "title": case "template": InHead(token); break; case "body": RaiseErrorOccurred(ErrorCode.BodyTagMisplaced); if (templateMode.Count == 0 && open.Count > 1 && open[1] is HTMLBodyElement) { frameset = false; AppendAttributes(htmlTagToken, open[1]); } break; case "frameset": RaiseErrorOccurred(ErrorCode.FramesetMisplaced); if (open.Count != 1 && open[1] is HTMLBodyElement && frameset) { open[1].ParentNode.RemoveChild(open[1]); while (open.Count > 1) { CloseCurrentNode(); } HTMLFrameSetElement element4 = new HTMLFrameSetElement(); AddElement(element4, htmlTagToken, false); insert = HtmlTreeMode.InFrameset; } break; case "address": case "article": case "aside": case "blockquote": case "center": case "details": case "dialog": case "dir": case "div": case "dl": case "fieldset": case "figcaption": case "figure": case "footer": case "header": case "hgroup": case "menu": case "nav": case "ol": case "p": case "section": case "summary": case "ul": if (IsInButtonScope()) InBodyEndTagParagraph(); AddElement(htmlTagToken, false); break; case "h1": case "h2": case "h3": case "h4": case "h5": case "h6": { if (IsInButtonScope()) InBodyEndTagParagraph(); if (CurrentNode is HTMLHeadingElement) { RaiseErrorOccurred(ErrorCode.HeadingNested); CloseCurrentNode(); } HTMLHeadingElement element9 = new HTMLHeadingElement(); AddElement(element9, htmlTagToken, false); break; } case "pre": case "listing": { if (IsInButtonScope()) InBodyEndTagParagraph(); HTMLPreElement element2 = new HTMLPreElement(); AddElement(element2, htmlTagToken, false); frameset = false; PreventNewLine(); break; } case "form": if (form == null) { if (IsInButtonScope()) InBodyEndTagParagraph(); HTMLFormElement element11 = new HTMLFormElement(); AddElement(element11, htmlTagToken, false); form = element11; } else RaiseErrorOccurred(ErrorCode.FormAlreadyOpen); break; case "li": InBodyStartTagListItem(htmlTagToken); break; case "dd": case "dt": InBodyStartTagDefinitionItem(htmlTagToken); break; case "plaintext": if (IsInButtonScope()) InBodyEndTagParagraph(); AddElement(token.AsTag(), false); tokenizer.Switch(HtmlParseMode.Plaintext); break; case "button": if (IsInScope<HTMLButtonElement>()) { RaiseErrorOccurred(ErrorCode.ButtonInScope); InBodyEndTagBlock("button"); InBody(token); } else { ReconstructFormatting(); HTMLButtonElement element13 = new HTMLButtonElement(); AddElement(element13, htmlTagToken, false); frameset = false; } break; case "a": { for (int num = formatting.Count - 1; num >= 0; num--) { if (formatting[num] == null) break; if (formatting[num] is HTMLAnchorElement) { Element item = formatting[num]; RaiseErrorOccurred(ErrorCode.AnchorNested); HeisenbergAlgorithm(HtmlToken.CloseTag("a")); if (open.Contains(item)) open.Remove(item); if (formatting.Contains(item)) formatting.RemoveAt(num); break; } } ReconstructFormatting(); HTMLAnchorElement element12 = new HTMLAnchorElement(); AddElement(element12, htmlTagToken, false); AddFormattingElement(element12); break; } case "b": case "big": case "code": case "em": case "font": case "i": case "s": case "small": case "strike": case "strong": case "tt": case "u": { ReconstructFormatting(); HTMLElement element10 = HTMLFactory.Create(htmlTagToken.Name, doc); AddElement(element10, htmlTagToken, false); AddFormattingElement(element10); break; } case "nobr": { ReconstructFormatting(); if (IsInScope<HTMLNoNewlineElement>()) { RaiseErrorOccurred(ErrorCode.NobrInScope); HeisenbergAlgorithm(htmlTagToken); ReconstructFormatting(); } HTMLElement element7 = HTMLFactory.Create(htmlTagToken.Name, doc); AddElement(element7, htmlTagToken, false); AddFormattingElement(element7); break; } case "applet": case "marquee": case "object": ReconstructFormatting(); AddElement(htmlTagToken, false); AddScopeMarker(); frameset = false; break; case "table": { if (doc.QuirksMode == QuirksMode.Off && IsInButtonScope()) InBodyEndTagParagraph(); HTMLTableElement element5 = new HTMLTableElement(); AddElement(element5, htmlTagToken, false); frameset = false; insert = HtmlTreeMode.InTable; break; } case "area": case "br": case "embed": case "keygen": case "wbr": case "img": InBodyStartTagBreakrow(htmlTagToken); break; case "image": RaiseErrorOccurred(ErrorCode.ImageTagNamedWrong); htmlTagToken.Name = "img"; InBodyStartTagBreakrow(htmlTagToken); break; case "input": { ReconstructFormatting(); HTMLInputElement element3 = new HTMLInputElement(); AddElement(element3, htmlTagToken, true); CloseCurrentNode(); if (!htmlTagToken.GetAttribute(AttributeNames.Type).Equals("hidden", StringComparison.OrdinalIgnoreCase)) frameset = false; break; } case "param": case "source": case "track": AddElement(htmlTagToken, true); CloseCurrentNode(); break; case "hr": { if (IsInButtonScope()) InBodyEndTagParagraph(); HTMLHRElement element = new HTMLHRElement(); AddElement(element, htmlTagToken, true); CloseCurrentNode(); frameset = false; break; } case "isindex": RaiseErrorOccurred(ErrorCode.TagInappropriate); if (form == null) { InBody(HtmlToken.OpenTag("form")); if (htmlTagToken.GetAttribute(AttributeNames.Action) != string.Empty) form.SetAttribute(AttributeNames.Action, htmlTagToken.GetAttribute(AttributeNames.Action)); InBody(HtmlToken.OpenTag("hr")); InBody(HtmlToken.OpenTag("label")); if (htmlTagToken.GetAttribute(AttributeNames.Prompt) != string.Empty) AddCharacters(htmlTagToken.GetAttribute(AttributeNames.Prompt)); else AddCharacters("This is a searchable index. Enter search keywords: "); HtmlTagToken htmlTagToken2 = HtmlToken.OpenTag("input"); htmlTagToken2.AddAttribute(AttributeNames.Name, "isindex"); for (int k = 0; k < htmlTagToken.Attributes.Count; k++) { if (!htmlTagToken.Attributes[k].Key.IsOneOf(AttributeNames.Name, AttributeNames.Action, AttributeNames.Prompt)) htmlTagToken2.AddAttribute(htmlTagToken.Attributes[k].Key, htmlTagToken.Attributes[k].Value); } InBody(htmlTagToken2); InBody(HtmlToken.CloseTag("label")); InBody(HtmlToken.OpenTag("hr")); InBody(HtmlToken.CloseTag("form")); } break; case "textarea": { HTMLTextAreaElement element8 = new HTMLTextAreaElement(); AddElement(element8, htmlTagToken, false); tokenizer.Switch(HtmlParseMode.RCData); originalInsert = insert; frameset = false; insert = HtmlTreeMode.Text; PreventNewLine(); break; } case "xmp": if (IsInButtonScope()) InBodyEndTagParagraph(); ReconstructFormatting(); frameset = false; RawtextAlgorithm(htmlTagToken); break; case "iframe": frameset = false; RawtextAlgorithm(htmlTagToken); break; case "select": { ReconstructFormatting(); HTMLSelectElement element6 = new HTMLSelectElement(); AddElement(element6, htmlTagToken, false); frameset = false; switch (insert) { case HtmlTreeMode.InTable: case HtmlTreeMode.InCaption: case HtmlTreeMode.InRow: case HtmlTreeMode.InCell: insert = HtmlTreeMode.InSelectInTable; break; default: insert = HtmlTreeMode.InSelect; break; } break; } case "optgroup": case "option": if (CurrentNode is HTMLOptionElement) InBodyEndTagAnythingElse(HtmlToken.CloseTag("option")); ReconstructFormatting(); AddElement(htmlTagToken, false); break; case "rp": case "rt": if (IsInScope<HTMLRubyElement>()) { GenerateImpliedEndTags(); if (!(CurrentNode is HTMLRubyElement)) RaiseErrorOccurred(ErrorCode.TagDoesNotMatchCurrentNode); } AddElement(htmlTagToken, false); break; case "noembed": RawtextAlgorithm(htmlTagToken); break; case "noscript": if (doc.Options.IsScripting) RawtextAlgorithm(htmlTagToken); else { ReconstructFormatting(); AddElement(htmlTagToken, false); } break; case "math": { MathElement mathElement = new MathElement(); mathElement.NodeName = htmlTagToken.Name; ReconstructFormatting(); for (int j = 0; j < htmlTagToken.Attributes.Count; j++) { string key2 = htmlTagToken.Attributes[j].Key; string value2 = htmlTagToken.Attributes[j].Value; mathElement.SetAdjustedAttribute(key2.AdjustMathMLAttributeName(), value2); } AddElement(mathElement); if (htmlTagToken.IsSelfClosing) open.Remove(mathElement); break; } case "svg": { SVGElement sVGElement = new SVGElement(); sVGElement.NodeName = htmlTagToken.Name; ReconstructFormatting(); for (int i = 0; i < htmlTagToken.Attributes.Count; i++) { string key = htmlTagToken.Attributes[i].Key; string value = htmlTagToken.Attributes[i].Value; sVGElement.SetAdjustedAttribute(key.AdjustSvgAttributeName(), value); } AddElement(sVGElement); if (htmlTagToken.IsSelfClosing) open.Remove(sVGElement); break; } case "caption": case "col": case "colgroup": case "frame": case "head": case "tbody": case "td": case "tfoot": case "th": case "thead": case "tr": RaiseErrorOccurred(ErrorCode.TagCannotStartHere); break; default: ReconstructFormatting(); AddElement(htmlTagToken, false); break; } } else if (token.Type == HtmlTokenType.EndTag) { HtmlTagToken htmlTagToken3 = (HtmlTagToken)token; switch (htmlTagToken3.Name) { case "body": InBodyEndTagBody(); break; case "html": if (InBodyEndTagBody()) AfterBody(token); break; case "address": case "article": case "aside": case "blockquote": case "button": case "center": case "details": case "dialog": case "dir": case "div": case "dl": case "fieldset": case "figcaption": case "figure": case "footer": case "header": case "hgroup": case "listing": case "main": case "menu": case "nav": case "ol": case "pre": case "section": case "summary": case "ul": InBodyEndTagBlock(htmlTagToken3.Name); break; case "template": InHead(htmlTagToken3); break; case "form": { HTMLFormElement hTMLFormElement = form; form = null; if (hTMLFormElement != null && IsInScope(hTMLFormElement.NodeName)) { GenerateImpliedEndTags(); if (CurrentNode != hTMLFormElement) RaiseErrorOccurred(ErrorCode.FormClosedWrong); open.Remove(hTMLFormElement); } else RaiseErrorOccurred(ErrorCode.FormNotInScope); break; } case "p": InBodyEndTagParagraph(); break; case "li": if (IsInListItemScope()) { GenerateImpliedEndTagsExceptFor(htmlTagToken3.Name); if (!(CurrentNode is HTMLLIElement)) RaiseErrorOccurred(ErrorCode.TagDoesNotMatchCurrentNode); ClearStackBackTo<HTMLLIElement>(); CloseCurrentNode(); } else RaiseErrorOccurred(ErrorCode.ListItemNotInScope); break; case "dd": case "dt": if (IsInScope(htmlTagToken3.Name)) { GenerateImpliedEndTagsExceptFor(htmlTagToken3.Name); if (CurrentNode.NodeName != htmlTagToken3.Name) RaiseErrorOccurred(ErrorCode.TagDoesNotMatchCurrentNode); ClearStackBackTo(htmlTagToken3.Name); CloseCurrentNode(); } else RaiseErrorOccurred(ErrorCode.ListItemNotInScope); break; case "h1": case "h2": case "h3": case "h4": case "h5": case "h6": if (IsInScope<HTMLHeadingElement>()) { GenerateImpliedEndTags(); if (CurrentNode.NodeName != htmlTagToken3.Name) RaiseErrorOccurred(ErrorCode.TagDoesNotMatchCurrentNode); ClearStackBackTo<HTMLHeadingElement>(); CloseCurrentNode(); } else RaiseErrorOccurred(ErrorCode.HeadingNotInScope); break; case "a": case "b": case "big": case "code": case "em": case "font": case "i": case "nobr": case "s": case "small": case "strike": case "strong": case "tt": case "u": HeisenbergAlgorithm(htmlTagToken3); break; case "applet": case "marquee": case "object": if (IsInScope(htmlTagToken3.Name)) { GenerateImpliedEndTags(); if (CurrentNode.NodeName != htmlTagToken3.Name) RaiseErrorOccurred(ErrorCode.TagDoesNotMatchCurrentNode); ClearStackBackTo(htmlTagToken3.Name); CloseCurrentNode(); ClearFormattingElements(); } else RaiseErrorOccurred(ErrorCode.ObjectNotInScope); break; case "br": RaiseErrorOccurred(ErrorCode.TagCannotEndHere); InBodyStartTagBreakrow(HtmlToken.OpenTag("br")); break; default: InBodyEndTagAnythingElse(htmlTagToken3); break; } } else if (token.Type == HtmlTokenType.EOF) { CheckBodyOnClosing(); if (templateMode.Count != 0) InTemplate(token); else End(); } } private void Text(HtmlToken token) { if (token.Type == HtmlTokenType.Character) AddCharacters(((HtmlCharacterToken)token).Data); else if (token.Type == HtmlTokenType.EOF) { RaiseErrorOccurred(ErrorCode.EOF); CloseCurrentNode(); insert = originalInsert; Consume(token); } else if (token.Type == HtmlTokenType.EndTag && ((HtmlTagToken)token).Name != "script") { CloseCurrentNode(); insert = originalInsert; } else if (token.Type == HtmlTokenType.EndTag) { RunScript(); } } private void InTable(HtmlToken token) { if (token.Type == HtmlTokenType.Comment) AddComment(token); else if (token.Type == HtmlTokenType.DOCTYPE) { RaiseErrorOccurred(ErrorCode.DoctypeTagInappropriate); } else if (token.Type == HtmlTokenType.StartTag) { HtmlTagToken htmlTagToken = (HtmlTagToken)token; switch (htmlTagToken.Name) { case "caption": { ClearStackBackTo<HTMLTableElement>(); AddScopeMarker(); HTMLTableCaptionElement element5 = new HTMLTableCaptionElement(); AddElement(element5, htmlTagToken, false); insert = HtmlTreeMode.InCaption; break; } case "colgroup": { ClearStackBackTo<HTMLTableElement>(); HTMLTableColElement element4 = new HTMLTableColElement(); AddElement(element4, htmlTagToken, false); insert = HtmlTreeMode.InColumnGroup; break; } case "col": InTable(HtmlToken.OpenTag("colgroup")); InColumnGroup(token); break; case "tbody": case "thead": case "tfoot": { ClearStackBackTo<HTMLTableElement>(); HTMLTableSectionElement element2 = new HTMLTableSectionElement(); AddElement(element2, htmlTagToken, false); insert = HtmlTreeMode.InTableBody; break; } case "td": case "th": case "tr": InTable(HtmlToken.OpenTag("tbody")); InTableBody(token); break; case "table": RaiseErrorOccurred(ErrorCode.TableNesting); if (InTableEndTagTable()) Home(token); break; case "script": case "style": case "template": InHead(token); break; case "input": if (htmlTagToken.GetAttribute(AttributeNames.Type).Equals("hidden", StringComparison.OrdinalIgnoreCase)) { RaiseErrorOccurred(ErrorCode.InputUnexpected); HTMLInputElement element3 = new HTMLInputElement(); AddElement(element3, htmlTagToken, true); CloseCurrentNode(); } else { RaiseErrorOccurred(ErrorCode.TokenNotPossible); InBodyWithFoster(token); } break; case "form": RaiseErrorOccurred(ErrorCode.FormInappropriate); if (form == null) { HTMLFormElement element = new HTMLFormElement(); AddElement(element, htmlTagToken, false); form = element; CloseCurrentNode(); } break; default: RaiseErrorOccurred(ErrorCode.IllegalElementInTableDetected); InBodyWithFoster(token); break; } } else if (token.Type == HtmlTokenType.EndTag) { HtmlTagToken htmlTagToken2 = (HtmlTagToken)token; switch (htmlTagToken2.Name) { case "table": InTableEndTagTable(); break; case "template": InHead(token); break; case "body": case "colgroup": case "col": case "caption": case "html": case "tbody": case "tr": case "thead": case "th": case "tfoot": case "td": RaiseErrorOccurred(ErrorCode.TagCannotEndHere); break; default: RaiseErrorOccurred(ErrorCode.IllegalElementInTableDetected); InBodyWithFoster(token); break; } } else if (token.Type == HtmlTokenType.Character && CurrentNode != null && CurrentNode.IsTableElement()) { InTableText((HtmlCharacterToken)token); } else if (token.Type == HtmlTokenType.EOF) { InBody(token); } else { RaiseErrorOccurred(ErrorCode.TokenNotPossible); InBodyWithFoster(token); } } private void InTableText(HtmlCharacterToken token) { bool hasContent = token.HasContent; if (hasContent) RaiseErrorOccurred(ErrorCode.TokenNotPossible); if (hasContent) InBodyWithFoster(token); else AddCharacters(token.Data); } private void InCaption(HtmlToken token) { if (token.Type == HtmlTokenType.EndTag) { HtmlTagToken htmlTagToken = (HtmlTagToken)token; switch (htmlTagToken.Name) { case "caption": InCaptionEndTagCaption(); break; case "body": case "th": case "colgroup": case "html": case "tbody": case "col": case "tfoot": case "td": case "thead": case "tr": RaiseErrorOccurred(ErrorCode.TagCannotEndHere); break; case "table": RaiseErrorOccurred(ErrorCode.TableNesting); if (InCaptionEndTagCaption()) InTable(token); break; default: InBody(token); break; } } else if (token.Type == HtmlTokenType.StartTag) { HtmlTagToken htmlTagToken2 = (HtmlTagToken)token; switch (htmlTagToken2.Name) { case "caption": case "col": case "colgroup": case "tbody": case "td": case "tfoot": case "th": case "thead": case "tr": RaiseErrorOccurred(ErrorCode.TagCannotStartHere); if (InCaptionEndTagCaption()) InTable(token); break; default: InBody(token); break; } } else { InBody(token); } } private void InColumnGroup(HtmlToken token) { if (token.Type == HtmlTokenType.Character) { HtmlCharacterToken htmlCharacterToken = (HtmlCharacterToken)token; string text = htmlCharacterToken.TrimStart(); AddCharacters(text); } else if (token.Type == HtmlTokenType.Comment) { AddComment(token); } else if (token.Type == HtmlTokenType.DOCTYPE) { RaiseErrorOccurred(ErrorCode.DoctypeTagInappropriate); } else if (token.IsStartTag("html")) { InBody(token); } else if (token.IsStartTag("col")) { HTMLTableColElement element = new HTMLTableColElement(); AddElement(element, token.AsTag(), true); CloseCurrentNode(); } else if (token.IsEndTag("colgroup")) { InColumnGroupEndTagColgroup(); } else if (token.IsEndTag("col")) { RaiseErrorOccurred(ErrorCode.TagClosedWrong); } else if (token.IsTag("template")) { InHead(token); } else if (token.Type == HtmlTokenType.EOF) { InBody(token); } else if (InColumnGroupEndTagColgroup()) { InTable(token); } } private void InTableBody(HtmlToken token) { if (token.Type == HtmlTokenType.StartTag) { HtmlTagToken htmlTagToken = (HtmlTagToken)token; if (htmlTagToken.Name == "tr") { ClearStackBackTo<HTMLTableSectionElement>(); HTMLTableRowElement element = new HTMLTableRowElement(); AddElement(element, token.AsTag(), false); insert = HtmlTreeMode.InRow; } else if (htmlTagToken.Name.IsTableCellElement()) { InTableBody(HtmlToken.OpenTag("tr")); InRow(token); } else if (htmlTagToken.Name.IsGeneralTableElement(false)) { InTableBodyCloseTable(htmlTagToken); } else { InTable(token); } } else if (token.Type == HtmlTokenType.EndTag) { HtmlTagToken htmlTagToken2 = (HtmlTagToken)token; if (htmlTagToken2.Name.IsTableSectionElement()) { if (IsInTableScope(((HtmlTagToken)token).Name)) { ClearStackBackTo<HTMLTableSectionElement>(); CloseCurrentNode(); insert = HtmlTreeMode.InTable; } else RaiseErrorOccurred(ErrorCode.TableSectionNotInScope); } else if (htmlTagToken2.Name.IsSpecialTableElement(true)) { RaiseErrorOccurred(ErrorCode.TagCannotEndHere); } else if (htmlTagToken2.Name == "table") { InTableBodyCloseTable(htmlTagToken2); } else { InTable(token); } } else { InTable(token); } } private void InRow(HtmlToken token) { if (token.Type == HtmlTokenType.StartTag) { HtmlTagToken htmlTagToken = (HtmlTagToken)token; if (htmlTagToken.Name.IsTableCellElement()) { ClearStackBackTo<HTMLTableRowElement>(); HTMLTableCellElement element = new HTMLTableCellElement(); AddElement(element, token.AsTag(), false); insert = HtmlTreeMode.InCell; AddScopeMarker(); } else if (htmlTagToken.Name.IsGeneralTableElement(true)) { if (InRowEndTagTablerow()) InTableBody(token); } else { InTable(token); } } else if (token.Type == HtmlTokenType.EndTag) { HtmlTagToken htmlTagToken2 = (HtmlTagToken)token; if (htmlTagToken2.Name == "tr") InRowEndTagTablerow(); else if (htmlTagToken2.Name == "table") { if (InRowEndTagTablerow()) InTableBody(token); } else if (htmlTagToken2.Name.IsTableSectionElement()) { if (IsInTableScope(htmlTagToken2.Name)) { InRowEndTagTablerow(); InTableBody(token); } else RaiseErrorOccurred(ErrorCode.TableSectionNotInScope); } else if (htmlTagToken2.Name.IsSpecialTableElement(false)) { RaiseErrorOccurred(ErrorCode.TagCannotEndHere); } else { InTable(token); } } else { InTable(token); } } private void InCell(HtmlToken token) { if (token.Type == HtmlTokenType.EndTag) { HtmlTagToken htmlTagToken = (HtmlTagToken)token; if (htmlTagToken.Name.IsTableCellElement()) InCellEndTagCell(); else if (htmlTagToken.Name.IsSpecialTableElement(false)) { RaiseErrorOccurred(ErrorCode.TagCannotEndHere); } else if (htmlTagToken.Name.IsTableElement()) { if (IsInTableScope(htmlTagToken.Name)) { InCellEndTagCell(); Home(token); } else RaiseErrorOccurred(ErrorCode.TableNotInScope); } else { InBody(token); } } else if (token.Type == HtmlTokenType.StartTag && (((HtmlTagToken)token).Name.IsGeneralTableElement(true) || ((HtmlTagToken)token).Name.IsTableCellElement())) { HtmlTagToken htmlTagToken2 = (HtmlTagToken)token; if (IsInTableScope("td") || IsInTableScope("th")) { InCellEndTagCell(); Home(token); } else RaiseErrorOccurred(ErrorCode.TableCellNotInScope); } else { InBody(token); } } private void InSelect(HtmlToken token) { if (token.Type == HtmlTokenType.Character) AddCharacters(((HtmlCharacterToken)token).Data); else if (token.Type == HtmlTokenType.Comment) { AddComment(token); } else if (token.Type == HtmlTokenType.DOCTYPE) { RaiseErrorOccurred(ErrorCode.DoctypeTagInappropriate); } else if (token.Type == HtmlTokenType.StartTag) { HtmlTagToken htmlTagToken = (HtmlTagToken)token; switch (htmlTagToken.Name) { case "html": InBody(token); break; case "option": { if (CurrentNode is HTMLOptionElement) InSelectEndTagOption(); HTMLOptionElement element2 = new HTMLOptionElement(); AddElement(element2, token.AsTag(), false); break; } case "optgroup": { if (CurrentNode is HTMLOptionElement) InSelectEndTagOption(); if (CurrentNode is HTMLOptGroupElement) InSelectEndTagOptgroup(); HTMLOptGroupElement element = new HTMLOptGroupElement(); AddElement(element, token.AsTag(), false); break; } case "select": RaiseErrorOccurred(ErrorCode.SelectNesting); InSelectEndTagSelect(); break; case "input": case "keygen": case "textarea": RaiseErrorOccurred(ErrorCode.IllegalElementInSelectDetected); if (IsInSelectScope("select")) { InSelectEndTagSelect(); Home(token); } break; case "template": case "script": InHead(token); break; default: RaiseErrorOccurred(ErrorCode.IllegalElementInSelectDetected); break; } } else if (token.Type == HtmlTokenType.EndTag) { HtmlTagToken htmlTagToken2 = (HtmlTagToken)token; switch (htmlTagToken2.Name) { case "template": InHead(token); break; case "optgroup": InSelectEndTagOptgroup(); break; case "option": InSelectEndTagOption(); break; case "select": if (IsInSelectScope("select")) InSelectEndTagSelect(); else RaiseErrorOccurred(ErrorCode.SelectNotInScope); break; default: RaiseErrorOccurred(ErrorCode.TagCannotEndHere); break; } } else if (token.Type == HtmlTokenType.EOF) { InBody(token); } else { RaiseErrorOccurred(ErrorCode.TokenNotPossible); } } private void InSelectInTable(HtmlToken token) { HtmlTagToken htmlTagToken = token as HtmlTagToken; if (htmlTagToken != null && (htmlTagToken.Name.IsTableCellElement() || htmlTagToken.Name.IsTableElement() || htmlTagToken.Name == "caption")) { if (token.Type == HtmlTokenType.StartTag) { RaiseErrorOccurred(ErrorCode.IllegalElementInSelectDetected); InSelectEndTagSelect(); Home(token); } else { RaiseErrorOccurred(ErrorCode.TagCannotEndHere); if (IsInTableScope(htmlTagToken.Name)) { InSelectEndTagSelect(); Home(token); } } } else InSelect(token); } private void InTemplate(HtmlToken token) { switch (token.Type) { case HtmlTokenType.DOCTYPE: case HtmlTokenType.Comment: case HtmlTokenType.Character: InBody(token); break; case HtmlTokenType.StartTag: { HtmlTagToken htmlTagToken = (HtmlTagToken)token; switch (htmlTagToken.Name) { case "base": case "basefont": case "link": case "meta": case "bgsound": case "noframes": case "script": case "style": case "template": case "title": InHead(token); break; case "caption": case "colgroup": case "tbody": case "tfoot": case "thead": TemplateStep(token, HtmlTreeMode.InTable); break; case "col": TemplateStep(token, HtmlTreeMode.InColumnGroup); break; case "tr": TemplateStep(token, HtmlTreeMode.InTableBody); break; case "td": case "th": TemplateStep(token, HtmlTreeMode.InRow); break; default: TemplateStep(token, HtmlTreeMode.InBody); break; } break; } case HtmlTokenType.EndTag: { HtmlTagToken htmlTagToken2 = (HtmlTagToken)token; if (htmlTagToken2.Name == "template") InHead(token); else RaiseErrorOccurred(ErrorCode.TagCannotEndHere); break; } case HtmlTokenType.EOF: if (TagCurrentlyOpen("template")) { RaiseErrorOccurred(ErrorCode.EOF); CloseTemplate(); Home(token); } else End(); break; } } private void AfterBody(HtmlToken token) { if (token.Type == HtmlTokenType.Character) { HtmlCharacterToken htmlCharacterToken = (HtmlCharacterToken)token; string text = htmlCharacterToken.TrimStart(); ReconstructFormatting(); AddCharacters(text); if (htmlCharacterToken.IsEmpty) return; } else { if (token.Type == HtmlTokenType.Comment) { AddComment(open[0], token); return; } if (token.Type == HtmlTokenType.DOCTYPE) { RaiseErrorOccurred(ErrorCode.DoctypeTagInappropriate); return; } if (token.IsTag("html")) { if (token.Type == HtmlTokenType.StartTag) InBody(token); else if (IsFragmentCase) { RaiseErrorOccurred(ErrorCode.TagInvalidInFragmentMode); } else { insert = HtmlTreeMode.AfterAfterBody; } return; } if (token.Type == HtmlTokenType.EOF) { End(); return; } } RaiseErrorOccurred(ErrorCode.TokenNotPossible); insert = HtmlTreeMode.InBody; InBody(token); } private void InFrameset(HtmlToken token) { if (token.Type == HtmlTokenType.Character) { HtmlCharacterToken htmlCharacterToken = (HtmlCharacterToken)token; string text = htmlCharacterToken.TrimStart(); AddCharacters(text); if (htmlCharacterToken.IsEmpty) return; } else { if (token.Type == HtmlTokenType.Comment) { AddComment(token); return; } if (token.Type == HtmlTokenType.DOCTYPE) { RaiseErrorOccurred(ErrorCode.DoctypeTagInappropriate); return; } if (token.Type == HtmlTokenType.StartTag) { HtmlTagToken htmlTagToken = (HtmlTagToken)token; if (htmlTagToken.Name == "html") { InBody(token); return; } if (htmlTagToken.Name == "frameset") { HTMLFrameSetElement element = new HTMLFrameSetElement(); AddElement(element, token.AsTag(), false); return; } if (htmlTagToken.Name == "frame") { HTMLFrameElement element2 = new HTMLFrameElement(); AddElement(element2, token.AsTag(), true); CloseCurrentNode(); return; } if (htmlTagToken.Name == "noframes") { InHead(token); return; } } else { if (token.IsEndTag("frameset")) { if (CurrentNode != open[0]) { CloseCurrentNode(); if (!IsFragmentCase && !(CurrentNode is HTMLFrameSetElement)) insert = HtmlTreeMode.AfterFrameset; } else RaiseErrorOccurred(ErrorCode.CurrentNodeIsRoot); return; } if (token.Type == HtmlTokenType.EOF) { if (CurrentNode != doc.DocumentElement) RaiseErrorOccurred(ErrorCode.CurrentNodeIsNotRoot); End(); return; } } } RaiseErrorOccurred(ErrorCode.TokenNotPossible); } private void AfterFrameset(HtmlToken token) { if (token.Type == HtmlTokenType.Character) { HtmlCharacterToken htmlCharacterToken = (HtmlCharacterToken)token; string text = htmlCharacterToken.TrimStart(); AddCharacters(text); if (htmlCharacterToken.IsEmpty) return; } else { if (token.Type == HtmlTokenType.Comment) { AddComment(token); return; } if (token.Type == HtmlTokenType.DOCTYPE) { RaiseErrorOccurred(ErrorCode.DoctypeTagInappropriate); return; } if (token.Type == HtmlTokenType.StartTag) { HtmlTagToken htmlTagToken = (HtmlTagToken)token; if (htmlTagToken.Name == "html") { InBody(token); return; } if (htmlTagToken.Name == "noframes") { InHead(token); return; } } else { if (token.IsEndTag("html")) { insert = HtmlTreeMode.AfterAfterFrameset; return; } if (token.Type == HtmlTokenType.EOF) { End(); return; } } } RaiseErrorOccurred(ErrorCode.TokenNotPossible); } private void AfterAfterBody(HtmlToken token) { if (token.Type == HtmlTokenType.Comment) AddComment(doc, token); else { if (token.Type == HtmlTokenType.Character) { HtmlCharacterToken htmlCharacterToken = (HtmlCharacterToken)token; string text = htmlCharacterToken.TrimStart(); ReconstructFormatting(); AddCharacters(text); if (htmlCharacterToken.IsEmpty) return; } else { if (token.Type == HtmlTokenType.DOCTYPE || token.IsStartTag("html")) { InBody(token); return; } if (token.Type == HtmlTokenType.EOF) { End(); return; } } RaiseErrorOccurred(ErrorCode.TokenNotPossible); insert = HtmlTreeMode.InBody; InBody(token); } } private void AfterAfterFrameset(HtmlToken token) { if (token.Type == HtmlTokenType.Comment) AddComment(doc, token); else { if (token.Type == HtmlTokenType.Character) { HtmlCharacterToken htmlCharacterToken = (HtmlCharacterToken)token; string text = htmlCharacterToken.TrimStart(); ReconstructFormatting(); AddCharacters(text); if (htmlCharacterToken.IsEmpty) return; } else { if (token.Type == HtmlTokenType.DOCTYPE || token.IsStartTag("html")) { InBody(token); return; } if (token.IsStartTag("noframes")) { InHead(token); return; } if (token.Type == HtmlTokenType.EOF) { End(); return; } } RaiseErrorOccurred(ErrorCode.TokenNotPossible); } } private void TemplateStep(HtmlToken token, HtmlTreeMode mode) { templateMode.Pop(); templateMode.Push(mode); insert = mode; Home(token); } private void CloseTemplate() { while (open.Count > 0) { Element currentNode = CurrentNode; CloseCurrentNode(); if (currentNode is HTMLTemplateElement) break; } ClearFormattingElements(); templateMode.Pop(); Reset(null); } private void InTableBodyCloseTable(HtmlTagToken tag) { if (IsInTableScope<HTMLTableSectionElement>()) { ClearStackBackTo<HTMLTableSectionElement>(); CloseCurrentNode(); insert = HtmlTreeMode.InTable; InTable(tag); } else RaiseErrorOccurred(ErrorCode.TableSectionNotInScope); } private void InSelectEndTagOption() { if (CurrentNode is HTMLOptionElement) CloseCurrentNode(); else RaiseErrorOccurred(ErrorCode.TagDoesNotMatchCurrentNode); } private void InSelectEndTagOptgroup() { if (open.Count > 1 && open[open.Count - 1] is HTMLOptionElement && open[open.Count - 2] is HTMLOptGroupElement) CloseCurrentNode(); if (CurrentNode is HTMLOptGroupElement) CloseCurrentNode(); else RaiseErrorOccurred(ErrorCode.TagDoesNotMatchCurrentNode); } private bool InColumnGroupEndTagColgroup() { if (CurrentNode.NodeName == "colgroup") { CloseCurrentNode(); insert = HtmlTreeMode.InTable; return true; } RaiseErrorOccurred(ErrorCode.TagDoesNotMatchCurrentNode); return false; } private void AfterHeadStartTagBody(HtmlTagToken token) { HTMLBodyElement element = new HTMLBodyElement(); AddElement(element, token, false); frameset = false; insert = HtmlTreeMode.InBody; } private void RawtextAlgorithm(HtmlTagToken tag) { HTMLElement element = HTMLFactory.Create(tag.Name, doc); AddElement(element, tag, false); originalInsert = insert; insert = HtmlTreeMode.Text; tokenizer.Switch(HtmlParseMode.Rawtext); } private void RCDataAlgorithm(HtmlTagToken tag) { HTMLElement element = HTMLFactory.Create(tag.Name, doc); AddElement(element, tag, false); originalInsert = insert; insert = HtmlTreeMode.Text; tokenizer.Switch(HtmlParseMode.RCData); } private void InBodyStartTagListItem(HtmlTagToken tag) { frameset = false; int num = open.Count - 1; Element element = open[num]; while (true) { if (element is HTMLLIElement && element.NodeName == "li") { InBody(HtmlToken.CloseTag(element.NodeName)); break; } if (!(element is HTMLAddressElement) && !(element is HTMLDivElement) && !(element is HTMLParagraphElement) && element.IsSpecial) break; element = open[--num]; } if (IsInButtonScope()) InBodyEndTagParagraph(); HTMLElement element2 = HTMLFactory.Create(tag.Name, doc); AddElement(element2, tag, false); } private void InBodyStartTagDefinitionItem(HtmlTagToken tag) { frameset = false; int num = open.Count - 1; Element element = open[num]; while (true) { if (element is HTMLLIElement && (element.NodeName == "dd" || element.NodeName == "dt")) { InBody(HtmlToken.CloseTag(element.NodeName)); break; } if (!(element is HTMLAddressElement) && !(element is HTMLDivElement) && !(element is HTMLParagraphElement) && element.IsSpecial) break; element = open[--num]; } if (IsInButtonScope()) InBodyEndTagParagraph(); HTMLElement element2 = HTMLFactory.Create(tag.Name, doc); AddElement(element2, tag, false); } private bool InBodyEndTagBlock(string tagName) { if (IsInScope(tagName)) { GenerateImpliedEndTags(); if (CurrentNode.NodeName != tagName) RaiseErrorOccurred(ErrorCode.TagDoesNotMatchCurrentNode); ClearStackBackTo(tagName); CloseCurrentNode(); return true; } RaiseErrorOccurred(ErrorCode.BlockNotInScope); return false; } private void HeisenbergAlgorithm(HtmlTagToken tag) { int num = 0; int num2 = 0; int num3 = 0; int num4 = 0; Element element; Element element2; while (true) { if (num >= 8) return; num++; num4 = 0; element = null; for (int num5 = formatting.Count - 1; num5 >= 0; num5--) { if (formatting[num5] == null) break; if (formatting[num5].NodeName == tag.Name) { num4 = num5; element = formatting[num5]; break; } } if (element == null) { InBodyEndTagAnythingElse(tag); return; } int num6 = open.IndexOf(element); if (num6 == -1) { RaiseErrorOccurred(ErrorCode.FormattingElementNotFound); formatting.Remove(element); return; } if (!IsInScope(element.NodeName)) { RaiseErrorOccurred(ErrorCode.ElementNotInScope); return; } if (num6 != open.Count - 1) RaiseErrorOccurred(ErrorCode.TagClosedWrong); element2 = null; num3 = num4; for (int i = num6 + 1; i < open.Count; i++) { if (open[i].IsSpecial) { num4 = i; element2 = open[i]; break; } } if (element2 == null) break; Element element3 = open[num6 - 1]; num2 = 0; Element element4 = element2; Element element5 = element2; while (true) { num2++; element4 = open[--num4]; if (element4 == element) break; if (num2 > 3 && formatting.Contains(element4)) formatting.Remove(element4); if (!formatting.Contains(element4)) open.Remove(element4); else { Element element6 = CopyElement(element4); element3.AppendChild(element6); open[num4] = element6; for (int j = 0; j != formatting.Count; j++) { if (formatting[j] == element4) { formatting[j] = element6; break; } } element4 = element6; if (element5 == element2) num3++; if (element5.ParentNode != null) element5.ParentNode.RemoveChild(element5); element4.AppendChild(element5); element5 = element4; } } if (element3.IsTableElement()) AddElementWithFoster(element5); else { if (element5.ParentNode != null) element5.ParentNode.RemoveChild(element5); element3.AppendChild(element5); } Element element7 = CopyElement(element); while (element2.ChildNodes.Length > 0) { element7.AppendChild(element2.RemoveChild(element2.ChildNodes[0])); } element2.AppendChild(element7); formatting.Remove(element); formatting.Insert(num3, element7); open.Remove(element); open.Insert(open.IndexOf(element2) + 1, element7); } do { element2 = CurrentNode; CloseCurrentNode(); } while (element2 != element); formatting.Remove(element); } private Element CopyElement(Element element) { HTMLElement hTMLElement = HTMLFactory.Create(element.NodeName, doc); hTMLElement.NodeName = element.NodeName; for (int i = 0; i < element.Attributes.Length; i++) { Attr attr = element.Attributes[i]; hTMLElement.SetAttribute(attr.NodeName, attr.NodeValue); } return hTMLElement; } private void InBodyWithFoster(HtmlToken token) { foster = true; InBody(token); foster = false; } private void InBodyEndTagAnythingElse(HtmlTagToken tag) { int num = open.Count - 1; Element element = CurrentNode; while (true) { if (element.NodeName == tag.Name) { GenerateImpliedEndTagsExceptFor(tag.Name); if (element.NodeName == tag.Name) RaiseErrorOccurred(ErrorCode.TagClosedWrong); int num2 = open.Count - 1; while (num <= num2) { CloseCurrentNode(); num2--; } return; } if (element.IsSpecial) break; element = open[--num]; } RaiseErrorOccurred(ErrorCode.TagClosedWrong); } private bool InBodyEndTagBody() { if (IsInScope<HTMLBodyElement>()) { CheckBodyOnClosing(); insert = HtmlTreeMode.AfterBody; return true; } RaiseErrorOccurred(ErrorCode.BodyNotInScope); return false; } private void InBodyStartTagBreakrow(HtmlTagToken tag) { ReconstructFormatting(); HTMLElement element = HTMLFactory.Create(tag.Name, doc); AddElement(element, tag, false); CloseCurrentNode(); frameset = false; } private bool InBodyEndTagParagraph() { if (IsInButtonScope()) { GenerateImpliedEndTagsExceptFor("p"); if (!(CurrentNode is HTMLParagraphElement)) RaiseErrorOccurred(ErrorCode.TagDoesNotMatchCurrentNode); ClearStackBackTo<HTMLParagraphElement>(); CloseCurrentNode(); return true; } RaiseErrorOccurred(ErrorCode.ParagraphNotInScope); InBody(HtmlToken.OpenTag("p")); InBodyEndTagParagraph(); return false; } private bool InTableEndTagTable() { if (IsInTableScope<HTMLTableElement>()) { ClearStackBackTo<HTMLTableElement>(); CloseCurrentNode(); Reset(null); return true; } RaiseErrorOccurred(ErrorCode.TableNotInScope); return false; } private bool InRowEndTagTablerow() { if (IsInTableScope<HTMLTableRowElement>()) { ClearStackBackTo<HTMLTableRowElement>(); CloseCurrentNode(); insert = HtmlTreeMode.InTableBody; return true; } RaiseErrorOccurred(ErrorCode.TableRowNotInScope); return false; } private void InSelectEndTagSelect() { ClearStackBackTo<HTMLSelectElement>(); CloseCurrentNode(); Reset(null); } private bool InCaptionEndTagCaption() { if (IsInTableScope<HTMLTableCaptionElement>()) { GenerateImpliedEndTags(); if (!(CurrentNode is HTMLTableCaptionElement)) RaiseErrorOccurred(ErrorCode.TagDoesNotMatchCurrentNode); ClearStackBackTo<HTMLTableCaptionElement>(); CloseCurrentNode(); ClearFormattingElements(); insert = HtmlTreeMode.InTable; return true; } RaiseErrorOccurred(ErrorCode.CaptionNotInScope); return false; } private bool InCellEndTagCell() { if (IsInTableScope<HTMLTableCellElement>()) { GenerateImpliedEndTags(); if (!(CurrentNode is HTMLTableCellElement)) RaiseErrorOccurred(ErrorCode.TagDoesNotMatchCurrentNode); ClearStackBackTo<HTMLTableCellElement>(); CloseCurrentNode(); ClearFormattingElements(); insert = HtmlTreeMode.InRow; return true; } RaiseErrorOccurred(ErrorCode.TableCellNotInScope); return false; } private void Foreign(HtmlToken token) { if (token.Type == HtmlTokenType.Character) { HtmlCharacterToken htmlCharacterToken = (HtmlCharacterToken)token; AddCharacters(htmlCharacterToken.Data.Replace('', '�')); if (htmlCharacterToken.HasContent) frameset = false; } else if (token.Type == HtmlTokenType.Comment) { AddComment(token); } else if (token.Type == HtmlTokenType.DOCTYPE) { RaiseErrorOccurred(ErrorCode.DoctypeTagInappropriate); } else if (token.Type == HtmlTokenType.StartTag) { HtmlTagToken htmlTagToken = (HtmlTagToken)token; switch (htmlTagToken.Name) { case "b": case "big": case "blockquote": case "body": case "br": case "center": case "code": case "dd": case "div": case "dl": case "dt": case "em": case "embed": case "h1": case "h2": case "h3": case "h4": case "h5": case "h6": case "head": case "hr": case "i": case "img": case "li": case "listing": case "main": case "menu": case "meta": case "nobr": case "ol": case "p": case "pre": case "ruby": case "s": case "small": case "span": case "strong": case "strike": case "sub": case "sup": case "table": case "tt": case "u": case "ul": case "var": ForeignNormalTag(token); break; case "font": for (int i = 0; i != htmlTagToken.Attributes.Count; i++) { if (htmlTagToken.Attributes[i].Key.IsOneOf("color", "face", "size")) { ForeignNormalTag(token); return; } } ForeignSpecialTag(htmlTagToken); break; default: ForeignSpecialTag(htmlTagToken); break; } } else if (token.Type == HtmlTokenType.EndTag) { HtmlTagToken htmlTagToken2 = (HtmlTagToken)token; if (CurrentNode is HTMLScriptElement && htmlTagToken2.Name == "script") RunScript(); else { Element element = CurrentNode; if (element.NodeName != htmlTagToken2.Name) RaiseErrorOccurred(ErrorCode.TagClosingMismatch); int num = open.Count - 1; while (true) { if (num <= 0) return; if (element.NodeName.Equals(htmlTagToken2.Name, StringComparison.OrdinalIgnoreCase)) { open.RemoveRange(num + 1, open.Count - num - 1); CloseCurrentNode(); return; } element = open[num - 1]; if (element.IsInHtml) break; num--; } Home(token); } } } private void ForeignSpecialTag(HtmlTagToken tag) { Element element = CreateForeignElementFrom(tag); if (element != null) { AddForeignElement(element); if (!tag.IsSelfClosing) { open.Add(element); tokenizer.AcceptsCharacterData = true; } else if (tag.Name == "script") { Foreign(HtmlToken.CloseTag("script")); } } } private Element CreateForeignElementFrom(HtmlTagToken tag) { if (AdjustedCurrentNode.IsInMathML) { MathElement mathElement = MathFactory.Create(tag.Name, doc); for (int i = 0; i < tag.Attributes.Count; i++) { string key = tag.Attributes[i].Key; string value = tag.Attributes[i].Value; mathElement.SetAdjustedAttribute(key.AdjustMathMLAttributeName(), value); } return mathElement; } if (AdjustedCurrentNode.IsInSvg) { SVGElement sVGElement = SVGFactory.Create(tag.Name.AdjustSvgTagName(), doc); for (int j = 0; j < tag.Attributes.Count; j++) { string key2 = tag.Attributes[j].Key; string value2 = tag.Attributes[j].Value; sVGElement.SetAdjustedAttribute(key2.AdjustSvgAttributeName(), value2); } return sVGElement; } return null; } private void ForeignNormalTag(HtmlToken token) { RaiseErrorOccurred(ErrorCode.TagCannotStartHere); do { CloseCurrentNode(); } while (!CurrentNode.IsHtmlTIP && !CurrentNode.IsMathMLTIP && !CurrentNode.IsInHtml); Consume(token); } private bool IsInScope(string tagName) { for (int num = open.Count - 1; num >= 0; num--) { Element element = open[num]; if (element.NodeName == tagName) return true; if (element is IScopeElement) return false; } return false; } private bool IsInScope<T>() { for (int num = open.Count - 1; num >= 0; num--) { Element element = open[num]; if (element is T) return true; if (element is IScopeElement) return false; } return false; } private bool IsInListItemScope() { for (int num = open.Count - 1; num >= 0; num--) { Element element = open[num]; if (element is HTMLLIElement) return true; if (element is IListScopeElement) return false; } return false; } private bool IsInButtonScope() { for (int num = open.Count - 1; num >= 0; num--) { Element element = open[num]; if (element is HTMLParagraphElement) return true; if (element is IScopeElement || element is HTMLButtonElement) return false; } return false; } private bool IsInTableScope<T>() { for (int num = open.Count - 1; num >= 0; num--) { Element element = open[num]; if (element is T) return true; if (element is ITableScopeElement) return false; } return false; } private bool IsInTableScope(string tagName) { for (int num = open.Count - 1; num >= 0; num--) { Element element = open[num]; if (element.NodeName == tagName) return true; if (element is ITableScopeElement) return false; } return false; } private bool IsInSelectScope(string tagName) { for (int num = open.Count - 1; num >= 0; num--) { Element element = open[num]; if (element.NodeName == tagName) return true; if (!(element is ISelectScopeElement)) return false; } return false; } private void Kernel() { HtmlToken htmlToken; do { htmlToken = tokenizer.Get(); Consume(htmlToken); } while (htmlToken.Type != HtmlTokenType.EOF); } private void RunScript() { doc.PerformMicrotaskCheckpoint(); doc.ProvideStableState(); HTMLScriptElement hTMLScriptElement = (HTMLScriptElement)CurrentNode; CloseCurrentNode(); insert = originalInsert; int insertionPoint = tokenizer.Stream.InsertionPoint; nesting++; hTMLScriptElement.Prepare(); nesting--; tokenizer.Stream.InsertionPoint = insertionPoint; if (pendingParsingBlock != null && nesting == 0) { do { hTMLScriptElement = pendingParsingBlock; pendingParsingBlock = null; doc.WaitForReady(); insertionPoint = tokenizer.Stream.InsertionPoint; nesting++; hTMLScriptElement.Run(); nesting--; tokenizer.Stream.ResetInsertionPoint(); } while (pendingParsingBlock != null); } } private void CheckBodyOnClosing() { int num = 0; while (true) { if (num >= open.Count) return; if (!(open[num] is IImplClosed)) break; num++; } RaiseErrorOccurred(ErrorCode.BodyClosedWrong); } private bool TagCurrentlyOpen(string tagName) { for (int i = 0; i < open.Count; i++) { if (open[i].TagName == tagName) return true; } return false; } private void PreventNewLine() { HtmlToken htmlToken = tokenizer.Get(); if (htmlToken.Type == HtmlTokenType.Character) ((HtmlCharacterToken)htmlToken).RemoveNewLine(); Home(htmlToken); } private void SetCharset(string charset) { Encoding encoding = DocumentEncoding.Resolve(charset); if (encoding != null) { doc.InputEncoding = encoding.WebName; tokenizer.Stream.Encoding = encoding; } } private void End() { doc.ReadyState = Readiness.Interactive; while (open.Count != 0) { CloseCurrentNode(); } while (doc.ScriptsWaiting != 0) { doc.RunNextScript(); } doc.QueueTask(doc.RaiseDomContentLoaded); doc.QueueTask(doc.RaiseLoadedEvent); if (doc.IsInBrowsingContext) doc.QueueTask(doc.ShowPage); doc.QueueTask(doc.EmptyAppCache); if (doc.IsToBePrinted) doc.Print(); doc.QueueTask(doc.FinishLoading); } private void AddDoctype(HtmlDoctypeToken doctypeToken) { DocumentType documentType = new DocumentType(); documentType.SystemId = doctypeToken.SystemIdentifier; documentType.PublicId = doctypeToken.PublicIdentifier; documentType.Name = doctypeToken.Name; doc.AppendChild(documentType); } private void AddRoot(HtmlTagToken tag) { HTMLHtmlElement hTMLHtmlElement = new HTMLHtmlElement(); doc.AppendChild(hTMLHtmlElement); SetupElement(hTMLHtmlElement, tag, false); open.Add(hTMLHtmlElement); tokenizer.AcceptsCharacterData = false; hTMLHtmlElement.ApplyManifest(); } private void AddComment(HtmlToken commentToken) { HtmlCommentToken htmlCommentToken = (HtmlCommentToken)commentToken; Comment comment = new Comment(); comment.Data = htmlCommentToken.Data; CurrentNode.AppendChild(comment); } private void AddComment(Node parent, HtmlToken commentToken) { HtmlCommentToken htmlCommentToken = (HtmlCommentToken)commentToken; Comment comment = new Comment(); comment.Data = htmlCommentToken.Data; parent.AppendChild(comment); } private void CloseCurrentNode() { if (open.Count > 0) { open.RemoveAt(open.Count - 1); Node adjustedCurrentNode = AdjustedCurrentNode; tokenizer.AcceptsCharacterData = (adjustedCurrentNode != null && !adjustedCurrentNode.IsInHtml); } } private void SetupElement(Element element, HtmlTagToken tag, bool acknowledgeSelfClosing) { element.NodeName = tag.Name; if (tag.IsSelfClosing && !acknowledgeSelfClosing) RaiseErrorOccurred(ErrorCode.TagCannotBeSelfClosed); for (int i = 0; i < tag.Attributes.Count; i++) { element.SetAttribute(tag.Attributes[i].Key, tag.Attributes[i].Value); } } private void AddElement(HtmlTagToken tag, bool acknowledgeSelfClosing = false) { HTMLElement element = HTMLFactory.Create(tag.Name, doc); SetupElement(element, tag, acknowledgeSelfClosing); AddElement(element); } private void AddElement(Element element, HtmlTagToken tag, bool acknowledgeSelfClosing = false) { SetupElement(element, tag, acknowledgeSelfClosing); AddElement(element); } private void AddElement(Element element) { Element currentNode = CurrentNode; if (foster && currentNode.IsTableElement()) AddElementWithFoster(element); else currentNode.AppendChild(element); open.Add(element); tokenizer.AcceptsCharacterData = !element.IsInHtml; } private void AddElementWithFoster(Element element) { bool flag = false; int num = open.Count; while (--num != 0) { if (open[num] is HTMLTemplateElement) { HTMLTemplateElement hTMLTemplateElement = (HTMLTemplateElement)open[num]; hTMLTemplateElement.Content.AppendChild(element); return; } if (open[num] is HTMLTableElement) { flag = true; break; } } Node node = open[num].ParentNode ?? open[num + 1]; if (flag && open[num].ParentNode != null) { int num2 = 0; while (true) { if (num2 >= node.ChildNodes.Length) return; if (node.ChildNodes[num2] == open[num]) break; num2++; } node.InsertChild(num2, element); } else node.AppendChild(element); } private void AddForeignElement(Element element) { element.NamespaceURI = AdjustedCurrentNode.NamespaceURI; CurrentNode.AppendChild(element); } private void AddCharacters(string text) { if (!string.IsNullOrEmpty(text)) { if (foster && CurrentNode.IsTableElement()) AddCharactersWithFoster(text); else CurrentNode.AppendText(text); } } private void AddCharactersWithFoster(string text) { bool flag = false; int num = open.Count; while (--num != 0) { if (open[num] is HTMLTemplateElement) { HTMLTemplateElement hTMLTemplateElement = (HTMLTemplateElement)open[num]; hTMLTemplateElement.Content.AppendText(text); return; } if (open[num] is HTMLTableElement) { flag = true; break; } } Node node = open[num].ParentNode ?? open[num + 1]; if (flag && open[num].ParentNode != null) { int num2 = 0; while (true) { if (num2 >= node.ChildNodes.Length) return; if (node.ChildNodes[num2] == open[num]) break; num2++; } node.InsertText(num2, text); } else node.AppendText(text); } private void AppendAttributes(HtmlTagToken tag, Element element) { foreach (KeyValuePair<string, string> attribute in tag.Attributes) { if (!element.HasAttribute(attribute.Key)) element.SetAttribute(attribute.Key, attribute.Value); } } private void ClearStackBackTo(string tagName) { while (CurrentNode.NodeName != tagName && !(CurrentNode is HTMLHtmlElement) && !(CurrentNode is HTMLTemplateElement)) { CloseCurrentNode(); } } private void ClearStackBackTo<T>() { while (!(CurrentNode is T) && !(CurrentNode is HTMLHtmlElement) && !(CurrentNode is HTMLTemplateElement)) { CloseCurrentNode(); } } private void GenerateImpliedEndTagsExceptFor(string tagName) { while (CurrentNode is IImpliedEnd && !(CurrentNode.NodeName == tagName)) { CloseCurrentNode(); } } private void GenerateImpliedEndTags() { while (CurrentNode is IImpliedEnd) { CloseCurrentNode(); } } private void AddScopeMarker() { formatting.Add(null); } private void AddFormattingElement(Element element) { int num = 0; for (int num2 = formatting.Count - 1; num2 >= 0; num2--) { Element element2 = formatting[num2]; if (element2 == null) break; if (element2.NodeName == element.NodeName && element2.Attributes.Equals(element.Attributes) && element2.NamespaceURI == element.NamespaceURI) { num++; if (num == 3) { formatting.RemoveAt(num2); break; } } } formatting.Add(element); } private void ClearFormattingElements() { while (formatting.Count != 0) { int index = formatting.Count - 1; Element element = formatting[index]; formatting.RemoveAt(index); if (element == null) break; } } private void ReconstructFormatting() { if (formatting.Count != 0) { int i = formatting.Count - 1; Element element = formatting[i]; if (element != null && !open.Contains(element)) { while (i > 0) { element = formatting[--i]; if (element == null || open.Contains(element)) { i++; break; } } for (; i < formatting.Count; i++) { Element element2 = CopyElement(formatting[i]); AddElement(element2); formatting[i] = element2; } } } } private void RaiseErrorOccurred(ErrorCode code) { if (this.ParseError != null) { ParseErrorEventArgs parseErrorEventArgs = new ParseErrorEventArgs((int)code, Errors.GetError(code)); parseErrorEventArgs.Line = tokenizer.Stream.Line; parseErrorEventArgs.Column = tokenizer.Stream.Column; this.ParseError(this, parseErrorEventArgs); } } } }