summaryrefslogtreecommitdiff
path: root/tests
diff options
context:
space:
mode:
authorPaul Wicking <paul.wicking@qt.io>2023-04-07 08:30:54 +0200
committerPaul Wicking <paul.wicking@qt.io>2023-04-07 17:29:44 +0200
commitf8d73cf765c9c81d195ccd7e5f4f50574d82e859 (patch)
tree28cd69eb96bd6edea862da306c91a741c284be8b /tests
parent1c7cca268a06b5a3c34765e1e0e4dd1b020f3302 (diff)
downloadqttools-f8d73cf765c9c81d195ccd7e5f4f50574d82e859.tar.gz
QDoc: Prevent crash in WebXMLGenerator
`WebXMLGenerator::startLink` is responsible for writing the WebXML tags for links. The method takes a pointer to `Atom`, from which a string is obtained for use in parts of the output. In most locations, the callee pre-qualifies the validity of the pointer it passes to the method (e.g. `if (atom) startLink([...]`). However, there's an exception to this in `WebXMLGenerator::generateAnnotatedList`, which calls `Text::firstAtom()` -- that may return `nullptr` -- in the call to `startLink`. This is considered a valid use-case that occurs when there's only title/meta commands and no body in the documentation. In such a case, or if the string obtained from `Atom::string()` is empty, `WebXMLGenerator::startLink` is designed to fall back to the full name of the `Node` being processed. However, in the case when generating a link for an example, `Generator::exampleFileTitle()` is called to obtain a file name for the example, and the `Atom*` is dereferenced to obtain a string is input for the latter method. At that point, the `Atom*` may be an unguarded null pointer. This change updates the generatedOutput test for QDoc by adding a minimal documentation project that serves as means to reproduce a bug that was observed in Qt3D, and fixes the bug in QDoc. The documentation project is designed such that the preconditions outlined in the first paragraph are met; that is to say, the structure of the documentation is such that, for an `Atom` that's constructed while generating the documentation set, `Atom::firstAtom()` is going to return a null pointer. The change to the test serves to validate the bug fix as well as to guard for future regressions. Avoid the crash that would occur when dereferencing this null pointer in `WebXMLGenerator::startLink` by checking the validity of the `Atom*` before dereferencing it to obtain a string used as file title when generating a link for an example. Fixes: QTBUG-112641 Pick-to: 6.5 Change-Id: I3633e5473b60013968becac4cd7bdacdbbdcb9ff Reviewed-by: Topi Reiniƶ <topi.reinio@qt.io>
Diffstat (limited to 'tests')
-rw-r--r--tests/auto/qdoc/generatedoutput/expected_output/html/illformatted-examples.webxml31
-rw-r--r--tests/auto/qdoc/generatedoutput/expected_output/html/illformatteddocumentation-someexample-example.webxml8
-rw-r--r--tests/auto/qdoc/generatedoutput/expected_output/html/illformatteddocumentation.index13
-rw-r--r--tests/auto/qdoc/generatedoutput/testdata/illformatted_documentation/illformatted-examples.qdoc17
-rw-r--r--tests/auto/qdoc/generatedoutput/testdata/illformatted_documentation/illformatted_documentation.qdocconf12
-rw-r--r--tests/auto/qdoc/generatedoutput/testdata/illformatted_documentation/some_example.qdoc8
-rw-r--r--tests/auto/qdoc/generatedoutput/tst_generatedoutput.cpp9
7 files changed, 98 insertions, 0 deletions
diff --git a/tests/auto/qdoc/generatedoutput/expected_output/html/illformatted-examples.webxml b/tests/auto/qdoc/generatedoutput/expected_output/html/illformatted-examples.webxml
new file mode 100644
index 000000000..b49d1b297
--- /dev/null
+++ b/tests/auto/qdoc/generatedoutput/expected_output/html/illformatted-examples.webxml
@@ -0,0 +1,31 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<WebXML>
+ <document>
+ <page name="illformatted-examples.html" href="illformatted-examples.html" status="active" location="illformatted-examples.qdoc" documented="true" groups="all-examples" subtype="page" title="Test generated output for illformatted examples" fulltitle="Test generated output for illformatted examples" subtitle="" brief="Demonstrate correctness for example generation">
+ <contents name="qml-examples" title="QML Examples" level="1"/>
+ <contents name="c-examples" title="C++ Examples" level="1"/>
+ <description>
+ <brief>Demonstrate correctness for example generation.</brief>
+ <para>This test includes the following examples:</para>
+ <section id="qml-examples">
+ <heading level="1">QML Examples</heading>
+ <table width="100%">
+ <row>
+ <item>
+ <para>
+ <link raw="QDoc: some example" href="illformatteddocumentation-someexample-example.html" type="page" page="QDoc: some example"/>
+ </para>
+ </item>
+ <item>
+ <para></para>
+ </item>
+ </row>
+ </table>
+ </section>
+ <section id="c-examples">
+ <heading level="1">C++ Examples</heading>
+ </section>
+ </description>
+ </page>
+ </document>
+</WebXML>
diff --git a/tests/auto/qdoc/generatedoutput/expected_output/html/illformatteddocumentation-someexample-example.webxml b/tests/auto/qdoc/generatedoutput/expected_output/html/illformatteddocumentation-someexample-example.webxml
new file mode 100644
index 000000000..675e3d74f
--- /dev/null
+++ b/tests/auto/qdoc/generatedoutput/expected_output/html/illformatteddocumentation-someexample-example.webxml
@@ -0,0 +1,8 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<WebXML>
+ <document>
+ <page name="someexample" href="illformatteddocumentation-someexample-example.html" status="active" location="some_example.qdoc" documented="true" groups="illformatted-examples-qml" subtype="example" title="QDoc: some example" fulltitle="QDoc: some example" subtitle="">
+ <description/>
+ </page>
+ </document>
+</WebXML>
diff --git a/tests/auto/qdoc/generatedoutput/expected_output/html/illformatteddocumentation.index b/tests/auto/qdoc/generatedoutput/expected_output/html/illformatteddocumentation.index
new file mode 100644
index 000000000..eae4c7eda
--- /dev/null
+++ b/tests/auto/qdoc/generatedoutput/expected_output/html/illformatteddocumentation.index
@@ -0,0 +1,13 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE QDOCINDEX>
+<INDEX url="" title="IllformattedDocumentation Reference Documentation" version="" project="IllformattedDocumentation">
+ <namespace name="" status="active" access="public" module="illformatteddocumentation">
+ <page name="someexample" href="illformatteddocumentation-someexample-example.html" status="active" location="some_example.qdoc" documented="true" groups="illformatted-examples-qml" subtype="example" title="QDoc: some example" fulltitle="QDoc: some example" subtitle=""/>
+ <page name="illformatted-examples.html" href="illformatted-examples.html" status="active" location="illformatted-examples.qdoc" documented="true" groups="all-examples" subtype="page" title="Test generated output for illformatted examples" fulltitle="Test generated output for illformatted examples" subtitle="" brief="Demonstrate correctness for example generation">
+ <contents name="qml-examples" title="QML Examples" level="1"/>
+ <contents name="c-examples" title="C++ Examples" level="1"/>
+ </page>
+ <group name="all-examples" href="all-examples.html" status="internal" seen="false" title=""/>
+ <group name="illformatted-examples-qml" href="illformatted-examples-qml.html" status="internal" seen="false" title=""/>
+ </namespace>
+</INDEX>
diff --git a/tests/auto/qdoc/generatedoutput/testdata/illformatted_documentation/illformatted-examples.qdoc b/tests/auto/qdoc/generatedoutput/testdata/illformatted_documentation/illformatted-examples.qdoc
new file mode 100644
index 000000000..5bfa9e7f6
--- /dev/null
+++ b/tests/auto/qdoc/generatedoutput/testdata/illformatted_documentation/illformatted-examples.qdoc
@@ -0,0 +1,17 @@
+// Copyright (C) 2023 The Qt Company Ltd.
+// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR GFDL-1.3-no-invariants-only
+
+/*!
+ \page illformatted-examples.html
+ \ingroup all-examples
+ \title Test generated output for illformatted examples
+ \brief Demonstrate correctness for example generation.
+
+ This test includes the following examples:
+
+ \section1 QML Examples
+ \annotatedlist illformatted-examples-qml
+
+ \section1 C++ Examples
+ \annotatedlist illformatted-examples-cpp
+*/
diff --git a/tests/auto/qdoc/generatedoutput/testdata/illformatted_documentation/illformatted_documentation.qdocconf b/tests/auto/qdoc/generatedoutput/testdata/illformatted_documentation/illformatted_documentation.qdocconf
new file mode 100644
index 000000000..307dd36b1
--- /dev/null
+++ b/tests/auto/qdoc/generatedoutput/testdata/illformatted_documentation/illformatted_documentation.qdocconf
@@ -0,0 +1,12 @@
+include(../configs/config.qdocconf)
+project = IllformattedDocumentation
+
+headerdirs = .
+sourcedirs = .
+exampledirs = .
+
+outputformats = WebXML
+WebXML.quotinginformation = true
+WebXML.nosubdirs = true
+
+warninglimit = 3 # The broken example generates three warnings
diff --git a/tests/auto/qdoc/generatedoutput/testdata/illformatted_documentation/some_example.qdoc b/tests/auto/qdoc/generatedoutput/testdata/illformatted_documentation/some_example.qdoc
new file mode 100644
index 000000000..a64605b87
--- /dev/null
+++ b/tests/auto/qdoc/generatedoutput/testdata/illformatted_documentation/some_example.qdoc
@@ -0,0 +1,8 @@
+// Copyright (C) 2023 The Qt Company Ltd.
+// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR GFDL-1.3-no-invariants-only
+
+/*!
+ \example someexample
+ \title QDoc: some example
+ \ingroup illformatted-examples-qml
+*/
diff --git a/tests/auto/qdoc/generatedoutput/tst_generatedoutput.cpp b/tests/auto/qdoc/generatedoutput/tst_generatedoutput.cpp
index 16bb7dc7b..6b48d914d 100644
--- a/tests/auto/qdoc/generatedoutput/tst_generatedoutput.cpp
+++ b/tests/auto/qdoc/generatedoutput/tst_generatedoutput.cpp
@@ -27,6 +27,7 @@ private slots:
void webXmlFromCpp();
void webXmlFromQml();
void webXmlFromCppBug80259();
+ void illformated_documentation_caused_qtbug112641();
// DocBook generator
void docBookFromQDocFile();
@@ -291,6 +292,14 @@ void tst_generatedOutput::webXmlFromCppBug80259()
"html/index.webxml");
}
+void tst_generatedOutput::illformated_documentation_caused_qtbug112641()
+{
+ testAndCompare("testdata/illformatted_documentation/illformatted_documentation.qdocconf",
+ "html/illformatted-examples.webxml "
+ "html/illformatteddocumentation-someexample-example.webxml "
+ "html/illformatteddocumentation.index");
+}
+
void tst_generatedOutput::docBookFromQDocFile()
{
testAndCompare("testdata/configs/docbook_test.qdocconf",