diff options
author | Mitch Curtis <mitch.curtis@digia.com> | 2013-11-07 08:36:29 (GMT) |
---|---|---|
committer | The Qt Project <gerrit-noreply@qt-project.org> | 2013-11-07 12:56:40 (GMT) |
commit | 512a1ce0698d370c313bb561bbf078935fa0342e (patch) | |
tree | 4cbb038859c99aa81c99678c52f6a76de7aa615b /tests | |
parent | cab363afa347e22c5f738f15533489e0cd671d59 (diff) | |
download | Qt-512a1ce0698d370c313bb561bbf078935fa0342e.zip Qt-512a1ce0698d370c313bb561bbf078935fa0342e.tar.gz Qt-512a1ce0698d370c313bb561bbf078935fa0342e.tar.bz2 |
Disallow deep or widely nested entity references.
Nested references with a depth of 2 or greater will fail. References
that partially expand to greater than 1024 characters will also fail.
This is a backport of 46a8885ae486e238a39efa5119c2714f328b08e4.
Change-Id: I0c2e1fa13d6ccb5f88641dae2ed3f28bfdeaf609
Reviewed-by: Richard J. Moore <rich@kde.org>
Reviewed-by: Lars Knoll <lars.knoll@digia.com>
Diffstat (limited to 'tests')
4 files changed, 96 insertions, 0 deletions
diff --git a/tests/auto/qxmlsimplereader/tst_qxmlsimplereader.cpp b/tests/auto/qxmlsimplereader/tst_qxmlsimplereader.cpp index 942d9ea..2c04d8e 100644 --- a/tests/auto/qxmlsimplereader/tst_qxmlsimplereader.cpp +++ b/tests/auto/qxmlsimplereader/tst_qxmlsimplereader.cpp @@ -163,6 +163,7 @@ class tst_QXmlSimpleReader : public QObject void reportNamespace() const; void reportNamespace_data() const; void roundtripWithNamespaces() const; + void dtdRecursionLimit(); private: static QDomDocument fromByteArray(const QString &title, const QByteArray &ba, bool *ok); @@ -771,5 +772,62 @@ void tst_QXmlSimpleReader::roundtripWithNamespaces() const } } +class TestHandler : public QXmlDefaultHandler +{ +public: + TestHandler() : + recursionCount(0) + { + } + + bool internalEntityDecl(const QString &name, const QString &value) + { + ++recursionCount; + return QXmlDefaultHandler::internalEntityDecl(name, value); + } + + int recursionCount; +}; + +void tst_QXmlSimpleReader::dtdRecursionLimit() +{ + QFile file("xmldocs/2-levels-nested-dtd.xml"); + QVERIFY(file.open(QIODevice::ReadOnly)); + QXmlSimpleReader xmlReader; + { + QXmlInputSource *source = new QXmlInputSource(&file); + TestHandler handler; + xmlReader.setDeclHandler(&handler); + xmlReader.setErrorHandler(&handler); + QVERIFY(!xmlReader.parse(source)); + } + + file.close(); + file.setFileName("xmldocs/1-levels-nested-dtd.xml"); + QVERIFY(file.open(QIODevice::ReadOnly)); + { + QXmlInputSource *source = new QXmlInputSource(&file); + TestHandler handler; + xmlReader.setDeclHandler(&handler); + xmlReader.setErrorHandler(&handler); + QVERIFY(!xmlReader.parse(source)); + // The error wasn't because of the recursion limit being reached, + // it was because the document is not valid. + QVERIFY(handler.recursionCount < 2); + } + + file.close(); + file.setFileName("xmldocs/internal-entity-polynomial-attribute.xml"); + QVERIFY(file.open(QIODevice::ReadOnly)); + { + QXmlInputSource *source = new QXmlInputSource(&file); + TestHandler handler; + xmlReader.setDeclHandler(&handler); + xmlReader.setErrorHandler(&handler); + QVERIFY(!xmlReader.parse(source)); + QVERIFY(handler.recursionCount == 1); + } +} + QTEST_MAIN(tst_QXmlSimpleReader) #include "tst_qxmlsimplereader.moc" diff --git a/tests/auto/qxmlsimplereader/xmldocs/1-levels-nested-dtd.xml b/tests/auto/qxmlsimplereader/xmldocs/1-levels-nested-dtd.xml new file mode 100644 index 0000000..0dfc15b --- /dev/null +++ b/tests/auto/qxmlsimplereader/xmldocs/1-levels-nested-dtd.xml @@ -0,0 +1,12 @@ +<?xml version="1.0"?> +<!-- Test non-deterministic content model matching. + +Entity references are not part of the internal DTD subset (for good reason). + +--> +<!DOCTYPE root [ +<!ELEMENT e0 EMPTY> +<!ENTITY % e1 "(e0,e0)"> +<!ELEMENT root (%e1;)?> +]> +<root/>
\ No newline at end of file diff --git a/tests/auto/qxmlsimplereader/xmldocs/2-levels-nested-dtd.xml b/tests/auto/qxmlsimplereader/xmldocs/2-levels-nested-dtd.xml new file mode 100644 index 0000000..7ec06db --- /dev/null +++ b/tests/auto/qxmlsimplereader/xmldocs/2-levels-nested-dtd.xml @@ -0,0 +1,13 @@ +<?xml version="1.0"?> +<!-- Test non-deterministic content model matching. + +Entity references are not part of the internal DTD subset (for good reason). + +--> +<!DOCTYPE root [ +<!ELEMENT e0 EMPTY> +<!ENTITY % e1 "(e0,e0)"> +<!ENTITY % e2 "(%e1;,%e1;,%e1;,%e1;,%e1;,%e1;,%e1;,%e1;,%e1;,%e1;,%e1;,%e1;,%e1;)"> +<!ELEMENT root (%e2;)?> +]> +<root/> diff --git a/tests/auto/qxmlsimplereader/xmldocs/internal-entity-polynomial-attribute.xml b/tests/auto/qxmlsimplereader/xmldocs/internal-entity-polynomial-attribute.xml new file mode 100644 index 0000000..bbb88f3 --- /dev/null +++ b/tests/auto/qxmlsimplereader/xmldocs/internal-entity-polynomial-attribute.xml @@ -0,0 +1,13 @@ +<?xml version="1.0"?> +<!-- Test polynomial growth of expanded XML. + Expansion happens in an attribute. --> +<!DOCTYPE root [ +<!ELEMENT root EMPTY> +<!ATTLIST root id CDATA #IMPLIED> +<!ENTITY e1 "XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX"> +<!ENTITY e2 "&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;&e1;"> +<!ENTITY e3 "&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;&e2;"> +<!ENTITY e4 "&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;&e3;"> +]> +<root id="&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;&e4;"/> + |