diff options
Diffstat (limited to 'WebCore/dom/XMLTokenizerQt.cpp')
| -rw-r--r-- | WebCore/dom/XMLTokenizerQt.cpp | 200 |
1 files changed, 33 insertions, 167 deletions
diff --git a/WebCore/dom/XMLTokenizerQt.cpp b/WebCore/dom/XMLTokenizerQt.cpp index 16c637f..4e61715 100644 --- a/WebCore/dom/XMLTokenizerQt.cpp +++ b/WebCore/dom/XMLTokenizerQt.cpp @@ -50,6 +50,7 @@ #include "ScriptSourceCode.h" #include "ScriptValue.h" #include "TextResourceDecoder.h" +#include "TransformSource.h" #include <QDebug> #include <wtf/Platform.h> #include <wtf/StringExtras.h> @@ -65,7 +66,6 @@ using namespace std; namespace WebCore { -#if QT_VERSION >= 0x040400 class EntityResolver : public QXmlStreamEntityResolver { virtual QString resolveUndeclaredEntity(const QString &name); }; @@ -75,7 +75,6 @@ QString EntityResolver::resolveUndeclaredEntity(const QString &name) UChar c = decodeNamedEntity(name.toUtf8().constData()); return QString(c); } -#endif // -------------------------------- @@ -84,7 +83,6 @@ XMLTokenizer::XMLTokenizer(Document* _doc, FrameView* _view) , m_view(_view) , m_wroteText(false) , m_currentNode(_doc) - , m_currentNodeIsReferenced(false) , m_sawError(false) , m_sawXSLTransform(false) , m_sawFirstElement(false) @@ -103,9 +101,7 @@ XMLTokenizer::XMLTokenizer(Document* _doc, FrameView* _view) , m_scriptStartLine(0) , m_parsingFragment(false) { -#if QT_VERSION >= 0x040400 m_stream.setEntityResolver(new EntityResolver); -#endif } XMLTokenizer::XMLTokenizer(DocumentFragment* fragment, Element* parentElement) @@ -113,7 +109,6 @@ XMLTokenizer::XMLTokenizer(DocumentFragment* fragment, Element* parentElement) , m_view(0) , m_wroteText(false) , m_currentNode(fragment) - , m_currentNodeIsReferenced(fragment) , m_sawError(false) , m_sawXSLTransform(false) , m_sawFirstElement(false) @@ -132,8 +127,7 @@ XMLTokenizer::XMLTokenizer(DocumentFragment* fragment, Element* parentElement) , m_scriptStartLine(0) , m_parsingFragment(true) { - if (fragment) - fragment->ref(); + fragment->ref(); if (m_doc) m_doc->ref(); @@ -151,19 +145,6 @@ XMLTokenizer::XMLTokenizer(DocumentFragment* fragment, Element* parentElement) if (elemStack.isEmpty()) return; -#if QT_VERSION < 0x040400 - for (Element* element = elemStack.last(); !elemStack.isEmpty(); elemStack.removeLast()) { - if (NamedNodeMap* attrs = element->attributes()) { - for (unsigned i = 0; i < attrs->length(); i++) { - Attribute* attr = attrs->attributeItem(i); - if (attr->localName() == "xmlns") - m_defaultNamespaceURI = attr->value(); - else if (attr->prefix() == "xmlns") - m_prefixToNamespaceMap.set(attr->localName(), attr->value()); - } - } - } -#else QXmlStreamNamespaceDeclarations namespaces; for (Element* element = elemStack.last(); !elemStack.isEmpty(); elemStack.removeLast()) { if (NamedNodeMap* attrs = element->attributes()) { @@ -178,7 +159,6 @@ XMLTokenizer::XMLTokenizer(DocumentFragment* fragment, Element* parentElement) } m_stream.addExtraNamespaceDeclarations(namespaces); m_stream.setEntityResolver(new EntityResolver); -#endif // If the parent element is not in document tree, there may be no xmlns attribute; just default to the parent's namespace. if (m_defaultNamespaceURI.isNull() && !parentElement->inDocument()) @@ -187,14 +167,12 @@ XMLTokenizer::XMLTokenizer(DocumentFragment* fragment, Element* parentElement) XMLTokenizer::~XMLTokenizer() { - setCurrentNode(0); + clearCurrentNodeStack(); if (m_parsingFragment && m_doc) m_doc->deref(); if (m_pendingScript) m_pendingScript->removeClient(this); -#if QT_VERSION >= 0x040400 delete m_stream.entityResolver(); -#endif } void XMLTokenizer::doWrite(const String& parseString) @@ -209,27 +187,6 @@ void XMLTokenizer::doWrite(const String& parseString) QString data(parseString); if (!data.isEmpty()) { -#if QT_VERSION < 0x040400 - if (!m_sawFirstElement) { - int idx = data.indexOf(QLatin1String("<?xml")); - if (idx != -1) { - int start = idx + 5; - int end = data.indexOf(QLatin1String("?>"), start); - QString content = data.mid(start, end-start); - bool ok = true; - HashMap<String, String> attrs = parseAttributes(content, ok); - String version = attrs.get("version"); - String encoding = attrs.get("encoding"); - ExceptionCode ec = 0; - if (!m_parsingFragment) { - if (!version.isEmpty()) - m_doc->setXMLVersion(version, ec); - if (!encoding.isEmpty()) - m_doc->setXMLEncoding(encoding); - } - } - } -#endif m_stream.addData(data); parse(); } @@ -237,7 +194,7 @@ void XMLTokenizer::doWrite(const String& parseString) return; } -void XMLTokenizer::initializeParserContext(const char* chunk) +void XMLTokenizer::initializeParserContext(const char*) { m_parserStopped = false; m_sawError = false; @@ -248,45 +205,19 @@ void XMLTokenizer::initializeParserContext(const char* chunk) void XMLTokenizer::doEnd() { #if ENABLE(XSLT) - #warning Look at XMLTokenizerLibXml.cpp -#endif - - if (m_stream.error() == QXmlStreamReader::PrematureEndOfDocumentError || (m_wroteText && !m_sawFirstElement)) { - handleError(fatal, qPrintable(m_stream.errorString()), lineNumber(), - columnNumber()); + if (m_sawXSLTransform) { + m_doc->setTransformSource(new TransformSource(m_originalSourceForTransform)); + m_doc->setParsing(false); // Make the doc think it's done, so it will apply xsl sheets. + m_doc->updateStyleSelector(); + m_doc->setParsing(true); + m_parserStopped = true; } -} - -#if ENABLE(XSLT) -void* xmlDocPtrForString(DocLoader* docLoader, const String& source, const String& url) -{ - if (source.isEmpty()) - return 0; - - // Parse in a single chunk into an xmlDocPtr - // FIXME: Hook up error handlers so that a failure to parse the main document results in - // good error messages. - const UChar BOM = 0xFEFF; - const unsigned char BOMHighByte = *reinterpret_cast<const unsigned char*>(&BOM); - - xmlGenericErrorFunc oldErrorFunc = xmlGenericError; - void* oldErrorContext = xmlGenericErrorContext; - - setLoaderForLibXMLCallbacks(docLoader); - xmlSetGenericErrorFunc(0, errorFunc); - - xmlDocPtr sourceDoc = xmlReadMemory(reinterpret_cast<const char*>(source.characters()), - source.length() * sizeof(UChar), - url.latin1().data(), - BOMHighByte == 0xFF ? "UTF-16LE" : "UTF-16BE", - XSLT_PARSE_OPTIONS); - - setLoaderForLibXMLCallbacks(0); - xmlSetGenericErrorFunc(oldErrorContext, oldErrorFunc); +#endif - return sourceDoc; + if (m_stream.error() == QXmlStreamReader::PrematureEndOfDocumentError + || (m_wroteText && !m_sawFirstElement && !m_sawXSLTransform && !m_sawError)) + handleError(fatal, qPrintable(m_stream.errorString()), lineNumber(), columnNumber()); } -#endif int XMLTokenizer::lineNumber() const { @@ -513,14 +444,12 @@ void XMLTokenizer::startDocument() if (!m_parsingFragment) { m_doc->setXMLStandalone(m_stream.isStandaloneDocument(), ec); -#if QT_VERSION >= 0x040400 QStringRef version = m_stream.documentVersion(); if (!version.isEmpty()) m_doc->setXMLVersion(version, ec); QStringRef encoding = m_stream.documentEncoding(); if (!encoding.isEmpty()) m_doc->setXMLEncoding(encoding); -#endif } } @@ -594,7 +523,7 @@ void XMLTokenizer::parseStartElement() return; } - setCurrentNode(newElement.get()); + pushCurrentNode(newElement.get()); if (m_view && !newElement->attached()) newElement->attach(); @@ -607,18 +536,26 @@ void XMLTokenizer::parseEndElement() exitText(); Node* n = m_currentNode; - RefPtr<Node> parent = n->parentNode(); n->finishParsingChildren(); if (!n->isElementNode() || !m_view) { - setCurrentNode(parent.get()); + if (!m_currentNodeStack.isEmpty()) + popCurrentNode(); return; } Element* element = static_cast<Element*>(n); + + // The element's parent may have already been removed from document. + // Parsing continues in this case, but scripts aren't executed. + if (!element->inDocument()) { + popCurrentNode(); + return; + } + ScriptElement* scriptElement = toScriptElement(element); if (!scriptElement) { - setCurrentNode(parent.get()); + popCurrentNode(); return; } @@ -636,7 +573,8 @@ void XMLTokenizer::parseEndElement() if (!scriptHref.isEmpty()) { // we have a src attribute String scriptCharset = scriptElement->scriptCharset(); - if ((m_pendingScript = m_doc->docLoader()->requestScript(scriptHref, scriptCharset))) { + if (element->dispatchBeforeLoadEvent(scriptHref) && + (m_pendingScript = m_doc->docLoader()->requestScript(scriptHref, scriptCharset))) { m_scriptElement = element; m_pendingScript->addClient(this); @@ -646,10 +584,10 @@ void XMLTokenizer::parseEndElement() } else m_scriptElement = 0; } else - m_view->frame()->loader()->executeScript(ScriptSourceCode(scriptElement->scriptContent(), m_doc->url(), m_scriptStartLine)); + m_view->frame()->script()->executeScript(ScriptSourceCode(scriptElement->scriptContent(), m_doc->url(), m_scriptStartLine)); } m_requestingScript = false; - setCurrentNode(parent.get()); + popCurrentNode(); } void XMLTokenizer::parseCharacters() @@ -683,7 +621,7 @@ void XMLTokenizer::parseProcessingInstruction() #if ENABLE(XSLT) m_sawXSLTransform = !m_sawFirstElement && pi->isXSL(); - if (m_sawXSLTransform && !m_doc->transformSourceDocument())) + if (m_sawXSLTransform && !m_doc->transformSourceDocument()) stopParsing(); #endif } @@ -692,7 +630,7 @@ void XMLTokenizer::parseCdata() { exitText(); - RefPtr<Node> newNode = new CDATASection(m_doc, m_stream.text()); + RefPtr<Node> newNode = CDATASection::create(m_doc, m_stream.text()); if (!m_currentNode->addChild(newNode.get())) return; if (m_view && !newNode->attached()) @@ -703,7 +641,7 @@ void XMLTokenizer::parseComment() { exitText(); - RefPtr<Node> newNode = new Comment(m_doc, m_stream.text()); + RefPtr<Node> newNode = Comment::create(m_doc, m_stream.text()); m_currentNode->addChild(newNode.get()); if (m_view && !newNode->attached()) newNode->attach(); @@ -721,83 +659,11 @@ bool XMLTokenizer::hasError() const return m_stream.hasError(); } -#if QT_VERSION < 0x040400 -static QString parseId(const QString &dtd, int *pos, bool *ok) -{ - *ok = true; - int start = *pos + 1; - int end = start; - if (dtd.at(*pos) == QLatin1Char('\'')) - while (start < dtd.length() && dtd.at(end) != QLatin1Char('\'')) - ++end; - else if (dtd.at(*pos) == QLatin1Char('\"')) - while (start < dtd.length() && dtd.at(end) != QLatin1Char('\"')) - ++end; - else { - *ok = false; - return QString(); - } - *pos = end + 1; - return dtd.mid(start, end - start); -} -#endif - void XMLTokenizer::parseDtd() { -#if QT_VERSION >= 0x040400 QStringRef name = m_stream.dtdName(); QStringRef publicId = m_stream.dtdPublicId(); QStringRef systemId = m_stream.dtdSystemId(); -#else - QString dtd = m_stream.text().toString(); - - int start = dtd.indexOf("<!DOCTYPE ") + 10; - while (start < dtd.length() && dtd.at(start).isSpace()) - ++start; - int end = start; - while (start < dtd.length() && !dtd.at(end).isSpace()) - ++end; - QString name = dtd.mid(start, end - start); - - start = end; - while (start < dtd.length() && dtd.at(start).isSpace()) - ++start; - end = start; - while (start < dtd.length() && !dtd.at(end).isSpace()) - ++end; - QString id = dtd.mid(start, end - start); - start = end; - while (start < dtd.length() && dtd.at(start).isSpace()) - ++start; - QString publicId; - QString systemId; - if (id == QLatin1String("PUBLIC")) { - bool ok; - publicId = parseId(dtd, &start, &ok); - if (!ok) { - handleError(fatal, "Invalid DOCTYPE", lineNumber(), columnNumber()); - return; - } - while (start < dtd.length() && dtd.at(start).isSpace()) - ++start; - systemId = parseId(dtd, &start, &ok); - if (!ok) { - handleError(fatal, "Invalid DOCTYPE", lineNumber(), columnNumber()); - return; - } - } else if (id == QLatin1String("SYSTEM")) { - bool ok; - systemId = parseId(dtd, &start, &ok); - if (!ok) { - handleError(fatal, "Invalid DOCTYPE", lineNumber(), columnNumber()); - return; - } - } else if (id == QLatin1String("[") || id == QLatin1String(">")) { - } else { - handleError(fatal, "Invalid DOCTYPE", lineNumber(), columnNumber()); - return; - } -#endif //qDebug() << dtd << name << publicId << systemId; if ((publicId == QLatin1String("-//W3C//DTD XHTML 1.0 Transitional//EN")) |
