Index: Source/core/xml/parser/XMLDocumentParser.cpp |
diff --git a/Source/core/xml/parser/XMLDocumentParser.cpp b/Source/core/xml/parser/XMLDocumentParser.cpp |
index a7f927f952982a8fab2eab6a32929d1ab068de1f..0504abafd0df39b9f8ee5ec7c0b13080479ed9eb 100644 |
--- a/Source/core/xml/parser/XMLDocumentParser.cpp |
+++ b/Source/core/xml/parser/XMLDocumentParser.cpp |
@@ -380,25 +380,30 @@ void XMLDocumentParser::handleError(XMLErrors::ErrorType type, const char* forma |
stopParsing(); |
} |
-void XMLDocumentParser::enterText() |
+void XMLDocumentParser::createLeafTextNodeIfNeeded() |
{ |
+ if (m_leafTextNode) |
+ return; |
+ |
ASSERT(m_bufferedText.size() == 0); |
- ASSERT(!m_leafTextNode); |
m_leafTextNode = Text::create(m_currentNode->document(), ""); |
m_currentNode->parserAppendChild(m_leafTextNode.get()); |
} |
-void XMLDocumentParser::exitText() |
+bool XMLDocumentParser::updateLeafTextNode() |
{ |
if (isStopped()) |
- return; |
+ return false; |
if (!m_leafTextNode) |
- return; |
+ return true; |
m_leafTextNode->appendData(toString(m_bufferedText.data(), m_bufferedText.size())); |
m_bufferedText.clear(); |
m_leafTextNode = nullptr; |
+ |
+ // Mutation event handlers executed by appendData() might detach this parser. |
+ return !isStopped(); |
} |
void XMLDocumentParser::detach() |
@@ -428,7 +433,7 @@ void XMLDocumentParser::end() |
if (m_sawError) { |
insertErrorMessageBlock(); |
} else { |
- exitText(); |
+ updateLeafTextNode(); |
haraken
2015/08/04 12:37:58
Don't we need to early-return here?
sof
2015/08/04 12:42:35
No, we could be in a Stopped state and need to bot
sof
2015/08/04 13:52:31
Added clarifying comment.
|
document()->styleResolverChanged(); |
} |
@@ -992,7 +997,8 @@ void XMLDocumentParser::startElementNs(const AtomicString& localName, const Atom |
return; |
} |
- exitText(); |
+ if (!updateLeafTextNode()) |
+ return; |
AtomicString adjustedURI = uri; |
if (m_parsingFragment && adjustedURI.isNull()) { |
@@ -1069,7 +1075,8 @@ void XMLDocumentParser::endElementNs() |
// the end of this method. |
RefPtrWillBeRawPtr<XMLDocumentParser> protect(this); |
- exitText(); |
+ if (!updateLeafTextNode()) |
+ return; |
RefPtrWillBeRawPtr<ContainerNode> n = m_currentNode; |
if (m_currentNode->isElementNode()) |
@@ -1145,8 +1152,7 @@ void XMLDocumentParser::characters(const xmlChar* chars, int length) |
return; |
} |
- if (!m_leafTextNode) |
- enterText(); |
+ createLeafTextNodeIfNeeded(); |
m_bufferedText.append(chars, length); |
} |
@@ -1176,7 +1182,8 @@ void XMLDocumentParser::processingInstruction(const String& target, const String |
return; |
} |
- exitText(); |
+ if (!updateLeafTextNode()) |
+ return; |
// ### handle exceptions |
TrackExceptionState exceptionState; |
@@ -1218,7 +1225,8 @@ void XMLDocumentParser::cdataBlock(const String& text) |
return; |
} |
- exitText(); |
+ if (!updateLeafTextNode()) |
+ return; |
m_currentNode->parserAppendChild(CDATASection::create(m_currentNode->document(), text)); |
} |
@@ -1233,7 +1241,8 @@ void XMLDocumentParser::comment(const String& text) |
return; |
} |
- exitText(); |
+ if (!updateLeafTextNode()) |
+ return; |
m_currentNode->parserAppendChild(Comment::create(m_currentNode->document(), text)); |
} |
@@ -1264,7 +1273,7 @@ void XMLDocumentParser::startDocument(const String& version, const String& encod |
void XMLDocumentParser::endDocument() |
{ |
- exitText(); |
+ updateLeafTextNode(); |
} |
void XMLDocumentParser::internalSubset(const String& name, const String& externalID, const String& systemID) |