File poppler-CVE-2020-36023.patch of Package poppler.31252

From 238dc045beeeb1eb619f3fb6cb699ba36813222d Mon Sep 17 00:00:00 2001
From: Albert Astals Cid <aacid@kde.org>
Date: Mon, 21 Dec 2020 22:57:44 +0100
Subject: [PATCH] Fix infinite looping in cvtGlyph with broken files

---
 fofi/FoFiType1C.cc | 20 +++++++++++++++-----
 fofi/FoFiType1C.h  |  4 +++-
 2 files changed, 18 insertions(+), 6 deletions(-)

Index: poppler-0.79.0/fofi/FoFiType1C.cc
===================================================================
--- poppler-0.79.0.orig/fofi/FoFiType1C.cc
+++ poppler-0.79.0/fofi/FoFiType1C.cc
@@ -549,8 +549,9 @@ void FoFiType1C::convertToCIDType0(const
 	if (!ok) {
 	  subrIdx.pos = -1;
 	}
+	std::set<int> offsetBeingParsed;
 	cvtGlyph(val.pos, val.len, charStrings,
-		 &subrIdx, &privateDicts[fdSelect ? fdSelect[gid] : 0], true);
+		 &subrIdx, &privateDicts[fdSelect ? fdSelect[gid] : 0], true, offsetBeingParsed);
       }
     }
   }
@@ -1181,7 +1182,8 @@ void FoFiType1C::eexecCvtGlyph(Type1CEex
 
   // generate the charstring
   charBuf = new GooString();
-  cvtGlyph(offset, nBytes, charBuf, subrIdx, pDict, true);
+  std::set<int> offsetBeingParsed;
+  cvtGlyph(offset, nBytes, charBuf, subrIdx, pDict, true, offsetBeingParsed);
 
   buf = GooString::format("/{0:s} {1:d} RD ", glyphName, charBuf->getLength());
   eexecWrite(eb, buf->c_str());
@@ -1195,7 +1197,7 @@ void FoFiType1C::eexecCvtGlyph(Type1CEex
 
 void FoFiType1C::cvtGlyph(int offset, int nBytes, GooString *charBuf,
 			  Type1CIndex *subrIdx, Type1CPrivateDict *pDict,
-			  bool top) {
+			  bool top,  std::set<int> &offsetBeingParsed) {
   Type1CIndexVal val;
   bool ok, dFP;
   double d, dx, dy;
@@ -1203,6 +1205,12 @@ void FoFiType1C::cvtGlyph(int offset, in
   unsigned char byte;
   int pos, subrBias, start, i, k;
 
+  if (offsetBeingParsed.find(offset) != offsetBeingParsed.end()) {
+     return;
+  }
+
+  auto offsetEmplaceResult = offsetBeingParsed.emplace(offset);
+
   start = charBuf->getLength();
   if (top) {
     charBuf->append('\x49'); //73;
@@ -1360,7 +1368,7 @@ void FoFiType1C::cvtGlyph(int offset, in
 	  ok = true;
 	  getIndexVal(subrIdx, k, &val, &ok);
 	  if (likely(ok && val.pos != offset)) {
-	    cvtGlyph(val.pos, val.len, charBuf, subrIdx, pDict, false);
+	    cvtGlyph(val.pos, val.len, charBuf, subrIdx, pDict, false, offsetBeingParsed);
 	  }
 	} else {
 	  //~ error(-1, "Too few args to Type 2 callsubr");
@@ -1595,7 +1603,7 @@ void FoFiType1C::cvtGlyph(int offset, in
 	  ok = true;
 	  getIndexVal(&gsubrIdx, k, &val, &ok);
 	  if (likely(ok && val.pos != offset)) {
-	    cvtGlyph(val.pos, val.len, charBuf, subrIdx, pDict, false);
+	    cvtGlyph(val.pos, val.len, charBuf, subrIdx, pDict, false, offsetBeingParsed);
 	  }
 	} else {
 	  //~ error(-1, "Too few args to Type 2 callgsubr");
@@ -1823,6 +1831,8 @@ void FoFiType1C::cvtGlyph(int offset, in
       r2 = (byte + r2) * 52845 + 22719;
     }
   }
+
+  offsetBeingParsed.erase(offsetEmplaceResult.first);
 }
 
 void FoFiType1C::cvtGlyphWidth(bool useOp, GooString *charBuf,
Index: poppler-0.79.0/fofi/FoFiType1C.h
===================================================================
--- poppler-0.79.0.orig/fofi/FoFiType1C.h
+++ poppler-0.79.0/fofi/FoFiType1C.h
@@ -27,6 +27,8 @@
 
 #include "FoFiBase.h"
 
+#include <set>
+
 class GooString;
 
 //------------------------------------------------------------------------
@@ -210,7 +212,7 @@ private:
 		     Type1CPrivateDict *pDict);
   void cvtGlyph(int offset, int nBytes, GooString *charBuf,
 		Type1CIndex *subrIdx, Type1CPrivateDict *pDict,
-		bool top);
+		bool top, std::set<int> &offsetBeingParsed);
   void cvtGlyphWidth(bool useOp, GooString *charBuf,
 		     Type1CPrivateDict *pDict);
   void cvtNum(double x, bool isFP, GooString *charBuf) const;
openSUSE Build Service is sponsored by