https://bugs.gentoo.org/974278 https://codereview.qt-project.org/c/qt/qtsvg/+/732200 --- a/src/svg/qsvgstructure.cpp +++ b/src/svg/qsvgstructure.cpp @@ -415,7 +415,8 @@ const auto markers = markersForNode(node); for (auto &i : markers) { - QSvgMarker *markNode = static_cast(node->document()->namedNode(i.markerId)); - if (!markNode) + QSvgNode *referencedNode = node->document()->namedNode(i.markerId); + if (!referencedNode || referencedNode->type() != QSvgNode::Marker) continue; + QSvgMarker *markNode = static_cast(referencedNode); p->save(); @@ -722,6 +723,7 @@ // Chrome seems to return the mask of the mask if a mask is set on the mask if (this->hasMask()) { - QSvgMask *maskNode = static_cast(document()->namedNode(this->maskId())); - if (maskNode) { + QSvgNode *referencedNode = document()->namedNode(this->maskId()); + if (referencedNode && referencedNode->type() == QSvgNode::Mask) { + QSvgMask *maskNode = static_cast(referencedNode); QRectF boundsRect; return maskNode->createMask(p, states, localRect, &boundsRect); --- a/tests/auto/qsvgrenderer/tst_qsvgrenderer.cpp +++ b/tests/auto/qsvgrenderer/tst_qsvgrenderer.cpp @@ -1868,4 +1868,15 @@ QTest::newRow("excessive moveto in path") // id=406541912 << R"()"_ba; + // Bad-cast to QSvgMarker from QSvgLine -> Heap-buffer-overflow + QTest::newRow("line-as-marker") // id=496327371 + << R"-()-"_ba; + QTest::newRow("line-as-mask") // modeled after 496327371 to test similar problem, needs UBSAN + << R"-( + + + + + + )-"_ba; }