diff options
author | Stephan Bergmann <sbergman@redhat.com> | 2019-06-03 14:37:37 +0200 |
---|---|---|
committer | Thorsten Behrens <Thorsten.Behrens@CIB.de> | 2019-06-04 14:55:46 +0200 |
commit | ee6dd4d39e9169283e74a9210ace0b8f7f897da4 (patch) | |
tree | e12dae99c298de593ccc6bb395c148a19d437bf7 /emfio | |
parent | 80457313b4cf9e9d846c5c694500edb71cccb8d7 (diff) |
Avoid truncation of ±1E20 to long
With -fsanitize=float-cast-overflow, opening doc/abi5309-1.doc as obtained by
bin/get-bugzilla-attachments-by-mimetype (i.e., the attachment at
<https://bugzilla.abisource.com/show_bug.cgi?id=5309#c3>) fails with
> include/tools/helpers.hxx:76:79: runtime error: 1e+20 is outside the range of representable values of type 'long'
> #0 in FRound(double) at include/tools/helpers.hxx:76:79 (instdir/program/libtllo.so +0x3c13dd)
> #1 in ImplPolygon::ImplPolygon(basegfx::B2DPolygon const&) at tools/source/generic/poly.cxx:474:30 (instdir/program/libtllo.so +0x40f35f)
> #2 in tools::Polygon::Polygon(basegfx::B2DPolygon const&) at tools/source/generic/poly.cxx:1849:72 (instdir/program/libtllo.so +0x42c9ff)
> #3 in ImplPolyPolygon::ImplPolyPolygon(basegfx::B2DPolyPolygon const&) at tools/source/generic/poly2.cxx:482:28 (instdir/program/libtllo.so +0x45561e)
> #4 in tools::PolyPolygon::PolyPolygon(basegfx::B2DPolyPolygon const&) at tools/source/generic/poly2.cxx:463:25 (instdir/program/libtllo.so +0x45512d)
> #5 in emfio::MtfTools::DrawPolygon(tools::Polygon, bool) at emfio/source/reader/mtftools.cxx:1287:17 (instdir/program/../program/libemfiolo.so +0x1828d3)
> #6 in emfio::WmfReader::ReadRecordParams(unsigned short) at emfio/source/reader/wmfreader.cxx:367:21 (instdir/program/../program/libemfiolo.so +0x1cffde)
> #7 in emfio::WmfReader::ReadWMF() at emfio/source/reader/wmfreader.cxx:1425:29 (instdir/program/../program/libemfiolo.so +0x1f7567)
> #8 in emfio::emfreader::XEmfParser::getDecomposition(com::sun::star::uno::Reference<com::sun::star::io::XInputStream> const&, rtl::OUString const&, com::sun::star::uno::Sequence<com::sun::star::beans::PropertyValue> const&) at emfio/source/emfuno/xemfparser.cxx:152:108 (instdir/program/../program/libemfiolo.so +0x13795a)
> #9 in non-virtual thunk to emfio::emfreader::XEmfParser::getDecomposition(com::sun::star::uno::Reference<com::sun::star::io::XInputStream> const&, rtl::OUString const&, com::sun::star::uno::Sequence<com::sun::star::beans::PropertyValue> const&) at emfio/source/emfuno/xemfparser.cxx (instdir/program/../program/libemfiolo.so +0x138735)
> #10 in VectorGraphicData::ensureSequenceAndRange() at vcl/source/gdi/vectorgraphicdata.cxx:172:137 (instdir/program/libvcllo.so +0x86bdadf)
> #11 in VectorGraphicData::ensureReplacement() at vcl/source/gdi/vectorgraphicdata.cxx:138:5 (instdir/program/libvcllo.so +0x86bcb94)
> #12 in VectorGraphicData::getReplacement() const at vcl/source/gdi/vectorgraphicdata.cxx:286:45 (instdir/program/libvcllo.so +0x86c0a04)
> #13 in ImpGraphic::ImplSetPrefSize(Size const&) at vcl/source/gdi/impgraph.cxx:956:45 (instdir/program/libvcllo.so +0x7d05433)
> #14 in Graphic::SetPrefSize(Size const&) at vcl/source/gdi/graph.cxx:388:19 (instdir/program/libvcllo.so +0x7ca7e26)
> #15 in SvxMSDffManager::GetBLIPDirect(SvStream&, Graphic&, tools::Rectangle*) at filter/source/msfilter/msdffimp.cxx:6616:26 (instdir/program/../program/libmsfilterlo.so +0x9617bc)
> #16 in SvxMSDffManager::GetBLIP(unsigned long, Graphic&, tools::Rectangle*) at filter/source/msfilter/msdffimp.cxx:6453:23 (instdir/program/../program/libmsfilterlo.so +0x95f368)
> #17 in SvxMSDffManager::ImportGraphic(SvStream&, SfxItemSet&, DffObjData const&) at filter/source/msfilter/msdffimp.cxx:3821:24 (instdir/program/../program/libmsfilterlo.so +0x990678)
> #18 in SvxMSDffManager::ImportShape(DffRecordHeader const&, SvStream&, SvxMSDffClientData&, tools::Rectangle&, tools::Rectangle const&, int, int*) at filter/source/msfilter/msdffimp.cxx:4368:28 (instdir/program/../program/libmsfilterlo.so +0x9a221a)
> #19 in SvxMSDffManager::ImportObj(SvStream&, SvxMSDffClientData&, tools::Rectangle&, tools::Rectangle const&, int, int*) at filter/source/msfilter/msdffimp.cxx:4073:16 (instdir/program/../program/libmsfilterlo.so +0x9972d8)
> #20 in SvxMSDffManager::GetShape(unsigned long, SdrObject*&, SvxMSDffImportData&) at filter/source/msfilter/msdffimp.cxx:6377:23 (instdir/program/../program/libmsfilterlo.so +0x9dde0c)
> #21 in SwWW8ImplReader::Read_GrafLayer(long) at sw/source/filter/ww8/ww8graf.cxx:2567:34 (instdir/program/../program/libmswordlo.so +0x2c51a1f)
> #22 in SwWW8ImplReader::ReadChar(long, long) at sw/source/filter/ww8/ww8par.cxx:3697:17 (instdir/program/../program/libmswordlo.so +0x2db3a07)
> #23 in SwWW8ImplReader::ReadChars(int&, int, long, long) at sw/source/filter/ww8/ww8par.cxx:3484:27 (instdir/program/../program/libmswordlo.so +0x2dafba2)
> #24 in SwWW8ImplReader::ReadText(int, int, ManTypes) at sw/source/filter/ww8/ww8par.cxx:4045:22 (instdir/program/../program/libmswordlo.so +0x2d85c3e)
> #25 in SwWW8ImplReader::CoreLoad(WW8Glossary const*) at sw/source/filter/ww8/ww8par.cxx:5227:9 (instdir/program/../program/libmswordlo.so +0x2de3314)
> #26 in SwWW8ImplReader::LoadThroughDecryption(WW8Glossary*) at sw/source/filter/ww8/ww8par.cxx:5892:19 (instdir/program/../program/libmswordlo.so +0x2df31ad)
> #27 in SwWW8ImplReader::LoadDoc(WW8Glossary*) at sw/source/filter/ww8/ww8par.cxx:6196:19 (instdir/program/../program/libmswordlo.so +0x2dfe1ed)
> #28 in WW8Reader::Read(SwDoc&, rtl::OUString const&, SwPaM&, rtl::OUString const&) at sw/source/filter/ww8/ww8par.cxx:6347:26 (instdir/program/../program/libmswordlo.so +0x2e0301a)
> #29 in SwReader::Read(Reader const&) at sw/source/filter/basflt/shellio.cxx:188:22 (instdir/program/../program/libswlo.so +0x1041d2be)
> #30 in SwDocShell::ConvertFrom(SfxMedium&) at sw/source/uibase/app/docsh.cxx:261:26 (instdir/program/../program/libswlo.so +0x10fc4d98)
> #31 in SfxObjectShell::DoLoad(SfxMedium*) at sfx2/source/doc/objstor.cxx:768:23 (instdir/program/libsfxlo.so +0x49d934a)
[...]
To represent "negative" clip regions, basegfx/source/tools/b2dclipstate.cxx uses
an ugly hack of subtracting the region from a ±1E20 bounding box. This document
uses such a negative clip region with a 4504x633@(11301,38) rectangular hole.
(Though I don't know whether that's the real intention, or caused by LO
misparsing the input file format.)
So to avoid converting the ±1E20 bounding box from double to long, do the
intersection here with basegfx double values, and only convert the result to
tools long values. (There appears to be no implemenation of intersection with
a polypolygon for B2DPolyPolyon, just B2DClipState::intersectPolyPolygon.) (In
principle there could be loss of precision when aPolyPoly is converted to a
B2DPolyPolygon now, but that's unlikely with a typical IEEE 754 double with
52 bit mantissa.)
Change-Id: I82a9941b43d90153d63612147b2ca33fbca5f179
Reviewed-on: https://gerrit.libreoffice.org/73386
Tested-by: Jenkins
Reviewed-by: Thorsten Behrens <Thorsten.Behrens@CIB.de>
Diffstat (limited to 'emfio')
-rw-r--r-- | emfio/inc/mtftools.hxx | 1 | ||||
-rw-r--r-- | emfio/source/reader/mtftools.cxx | 5 |
2 files changed, 4 insertions, 2 deletions
diff --git a/emfio/inc/mtftools.hxx b/emfio/inc/mtftools.hxx index fc1ec644d9dc..6c1cb4c66621 100644 --- a/emfio/inc/mtftools.hxx +++ b/emfio/inc/mtftools.hxx @@ -279,6 +279,7 @@ namespace emfio bool isEmpty() const { return maClip.isCleared(); } + basegfx::utils::B2DClipState const & getClip() const { return maClip; } basegfx::B2DPolyPolygon const & getClipPath() const; bool operator==(const WinMtfClipPath& rPath) const diff --git a/emfio/source/reader/mtftools.cxx b/emfio/source/reader/mtftools.cxx index b29b0185ff1e..3d398d8bd5df 100644 --- a/emfio/source/reader/mtftools.cxx +++ b/emfio/source/reader/mtftools.cxx @@ -1283,8 +1283,9 @@ namespace emfio if ( mbComplexClip ) { tools::PolyPolygon aPolyPoly( rPolygon ); - tools::PolyPolygon aDest; - tools::PolyPolygon(maClipPath.getClipPath()).GetIntersection( aPolyPoly, aDest ); + auto tmp = maClipPath.getClip(); + tmp.intersectPolyPolygon(aPolyPoly.getB2DPolyPolygon()); + tools::PolyPolygon aDest(tmp.getClipPoly()); ImplDrawClippedPolyPolygon( aDest ); } else |