Use smart pointers for CFX_Font and CFX_Type3Font classes

For the class owned member variables, use std::unique_ptr or
std::vector for memory management.

BUG=pdfium:518

Review-Url: https://codereview.chromium.org/2169793002
diff --git a/core/fpdfapi/fpdf_font/cpdf_type3font.cpp b/core/fpdfapi/fpdf_font/cpdf_type3font.cpp
index 6c339ea..8e4ac56 100644
--- a/core/fpdfapi/fpdf_font/cpdf_type3font.cpp
+++ b/core/fpdfapi/fpdf_font/cpdf_type3font.cpp
@@ -21,10 +21,7 @@
   FXSYS_memset(m_CharWidthL, 0, sizeof(m_CharWidthL));
 }
 
-CPDF_Type3Font::~CPDF_Type3Font() {
-  for (auto it : m_CacheMap)
-    delete it.second;
-}
+CPDF_Type3Font::~CPDF_Type3Font() {}
 
 bool CPDF_Type3Font::IsType3Font() const {
   return true;
@@ -94,7 +91,7 @@
 
   auto it = m_CacheMap.find(charcode);
   if (it != m_CacheMap.end())
-    return it->second;
+    return it->second.get();
 
   const FX_CHAR* name =
       GetAdobeCharName(m_BaseEncoding, m_pCharNames, charcode);
@@ -116,7 +113,7 @@
   pNewChar->m_pForm->ParseContent(nullptr, nullptr, pNewChar.get(), level + 1);
   it = m_CacheMap.find(charcode);
   if (it != m_CacheMap.end())
-    return it->second;
+    return it->second.get();
 
   FX_FLOAT scale = m_FontMatrix.GetXUnit();
   pNewChar->m_Width = (int32_t)(pNewChar->m_Width * scale + 0.5f);
@@ -134,8 +131,8 @@
   rcBBox.bottom = FXSYS_round(char_rect.bottom * 1000);
 
   ASSERT(!pdfium::ContainsKey(m_CacheMap, charcode));
-  CPDF_Type3Char* pCachedChar = pNewChar.release();
-  m_CacheMap[charcode] = pCachedChar;
+  m_CacheMap[charcode] = std::move(pNewChar);
+  CPDF_Type3Char* pCachedChar = m_CacheMap[charcode].get();
   if (pCachedChar->m_pForm->GetPageObjectList()->empty())
     pCachedChar->m_pForm.reset();
   return pCachedChar;
diff --git a/core/fpdfapi/fpdf_font/cpdf_type3font.h b/core/fpdfapi/fpdf_font/cpdf_type3font.h
index 70992c9..c5e9953 100644
--- a/core/fpdfapi/fpdf_font/cpdf_type3font.h
+++ b/core/fpdfapi/fpdf_font/cpdf_type3font.h
@@ -8,6 +8,7 @@
 #define CORE_FPDFAPI_FPDF_FONT_CPDF_TYPE3FONT_H_
 
 #include <map>
+#include <memory>
 
 #include "core/fpdfapi/fpdf_font/cpdf_simplefont.h"
 #include "core/fxcrt/include/fx_coordinates.h"
@@ -50,7 +51,7 @@
   CPDF_Dictionary* m_pCharProcs;
   CPDF_Dictionary* m_pPageResources;
   CPDF_Dictionary* m_pFontResources;
-  std::map<uint32_t, CPDF_Type3Char*> m_CacheMap;
+  std::map<uint32_t, std::unique_ptr<CPDF_Type3Char>> m_CacheMap;
 };
 
 #endif  // CORE_FPDFAPI_FPDF_FONT_CPDF_TYPE3FONT_H_
diff --git a/core/fxge/ge/fx_ge_font.cpp b/core/fxge/ge/fx_ge_font.cpp
index bd0bb0e..1aa5f9f 100644
--- a/core/fxge/ge/fx_ge_font.cpp
+++ b/core/fxge/ge/fx_ge_font.cpp
@@ -32,6 +32,41 @@
     return nullptr;
   return new CFX_UnicodeEncodingEx(pFont, nEncodingID);
 }
+
+unsigned long FTStreamRead(FXFT_Stream stream,
+                           unsigned long offset,
+                           unsigned char* buffer,
+                           unsigned long count) {
+  if (count == 0)
+    return 0;
+
+  IFX_FileRead* pFile = static_cast<IFX_FileRead*>(stream->descriptor.pointer);
+  return pFile->ReadBlock(buffer, offset, count) ? count : 0;
+}
+
+void FTStreamClose(FXFT_Stream stream) {}
+
+FX_BOOL LoadFileImp(FXFT_Library library,
+                    FXFT_Face* Face,
+                    IFX_FileRead* pFile,
+                    int32_t faceIndex,
+                    std::unique_ptr<FXFT_StreamRec>* stream) {
+  std::unique_ptr<FXFT_StreamRec> stream1(new FXFT_StreamRec());
+  stream1->base = nullptr;
+  stream1->size = static_cast<unsigned long>(pFile->GetSize());
+  stream1->pos = 0;
+  stream1->descriptor.pointer = pFile;
+  stream1->close = FTStreamClose;
+  stream1->read = FTStreamRead;
+  FXFT_Open_Args args;
+  args.flags = FT_OPEN_STREAM;
+  args.stream = stream1.get();
+  if (FXFT_Open_Face(library, &args, faceIndex, Face))
+    return FALSE;
+  if (stream)
+    *stream = std::move(stream1);
+  return TRUE;
+}
 #endif  // PDF_ENABLE_XFA
 
 FXFT_Face FT_LoadFont(const uint8_t* pData, int size) {
@@ -48,8 +83,6 @@
 #else
     : m_Face(nullptr),
 #endif  // PDF_ENABLE_XFA
-      m_pSubstFont(nullptr),
-      m_pFontDataAllocation(nullptr),
       m_pFontData(nullptr),
       m_pGsubData(nullptr),
       m_dwSize(0),
@@ -67,7 +100,7 @@
 
   m_bLogic = TRUE;
   if (pFont->m_pSubstFont) {
-    m_pSubstFont = new CFX_SubstFont;
+    m_pSubstFont.reset(new CFX_SubstFont);
     m_pSubstFont->m_Charset = pFont->m_pSubstFont->m_Charset;
     m_pSubstFont->m_ExtHandle = pFont->m_pSubstFont->m_ExtHandle;
     m_pSubstFont->m_SubstFlags = pFont->m_pSubstFont->m_SubstFlags;
@@ -94,8 +127,6 @@
 #endif  // PDF_ENABLE_XFA
 
 CFX_Font::~CFX_Font() {
-  delete m_pSubstFont;
-  FX_Free(m_pFontDataAllocation);
 #ifdef PDF_ENABLE_XFA
   if (m_bLogic) {
     m_OtfFontData.DetachBuffer();
@@ -122,10 +153,12 @@
   ReleasePlatformResource();
 #endif
 }
+
 void CFX_Font::DeleteFace() {
   FXFT_Done_Face(m_Face);
   m_Face = nullptr;
 }
+
 void CFX_Font::LoadSubst(const CFX_ByteString& face_name,
                          FX_BOOL bTrueType,
                          uint32_t flags,
@@ -135,10 +168,10 @@
                          FX_BOOL bVertical) {
   m_bEmbedded = FALSE;
   m_bVertical = bVertical;
-  m_pSubstFont = new CFX_SubstFont;
+  m_pSubstFont.reset(new CFX_SubstFont);
   m_Face = CFX_GEModule::Get()->GetFontMgr()->FindSubstFont(
       face_name, bTrueType, flags, weight, italic_angle, CharsetCP,
-      m_pSubstFont);
+      m_pSubstFont.get());
 #if _FXM_PLATFORM_ == _FXM_PLATFORM_APPLE_
   if (m_pSubstFont->m_ExtHandle) {
     m_pPlatformFont = m_pSubstFont->m_ExtHandle;
@@ -150,49 +183,8 @@
     m_dwSize = FXFT_Get_Face_Stream_Size(m_Face);
   }
 }
-#ifdef PDF_ENABLE_XFA
-extern "C" {
-unsigned long _FTStreamRead(FXFT_Stream stream,
-                            unsigned long offset,
-                            unsigned char* buffer,
-                            unsigned long count) {
-  if (count == 0) {
-    return 0;
-  }
-  IFX_FileRead* pFile = (IFX_FileRead*)stream->descriptor.pointer;
-  int res = pFile->ReadBlock(buffer, offset, count);
-  if (res) {
-    return count;
-  }
-  return 0;
-}
-void _FTStreamClose(FXFT_Stream stream) {}
-};
-FX_BOOL _LoadFile(FXFT_Library library,
-                  FXFT_Face* Face,
-                  IFX_FileRead* pFile,
-                  FXFT_Stream* stream,
-                  int32_t faceIndex = 0) {
-  FXFT_Stream stream1 = (FXFT_Stream)FX_Alloc(uint8_t, sizeof(FXFT_StreamRec));
-  stream1->base = nullptr;
-  stream1->size = (unsigned long)pFile->GetSize();
-  stream1->pos = 0;
-  stream1->descriptor.pointer = pFile;
-  stream1->close = _FTStreamClose;
-  stream1->read = _FTStreamRead;
-  FXFT_Open_Args args;
-  args.flags = FT_OPEN_STREAM;
-  args.stream = stream1;
-  if (FXFT_Open_Face(library, &args, faceIndex, Face)) {
-    FX_Free(stream1);
-    return FALSE;
-  }
-  if (stream) {
-    *stream = stream1;
-  }
-  return TRUE;
-}
 
+#ifdef PDF_ENABLE_XFA
 FX_BOOL CFX_Font::LoadFile(IFX_FileRead* pFile,
                            int nFaceIndex,
                            int* pFaceCount) {
@@ -202,13 +194,13 @@
   pFontMgr->InitFTLibrary();
   FXFT_Library library = pFontMgr->GetFTLibrary();
 
-  FXFT_Stream stream = nullptr;
-  if (!_LoadFile(library, &m_Face, pFile, &stream, nFaceIndex))
+  std::unique_ptr<FXFT_StreamRec> stream;
+  if (!LoadFileImp(library, &m_Face, pFile, nFaceIndex, &stream))
     return FALSE;
 
   if (pFaceCount)
     *pFaceCount = (int)m_Face->num_faces;
-  m_pOwnedStream = stream;
+  m_pOwnedStream = stream.release();
   FXFT_Set_Pixel_Sizes(m_Face, 0, 64);
   return TRUE;
 }
@@ -233,10 +225,10 @@
 }
 
 FX_BOOL CFX_Font::LoadEmbedded(const uint8_t* data, uint32_t size) {
-  m_pFontDataAllocation = FX_Alloc(uint8_t, size);
-  FXSYS_memcpy(m_pFontDataAllocation, data, size);
-  m_Face = FT_LoadFont(m_pFontDataAllocation, size);
-  m_pFontData = m_pFontDataAllocation;
+  std::vector<uint8_t> temp(data, data + size);
+  m_pFontDataAllocation.swap(temp);
+  m_Face = FT_LoadFont(m_pFontDataAllocation.data(), size);
+  m_pFontData = m_pFontDataAllocation.data();
   m_bEmbedded = TRUE;
   m_dwSize = size;
   return !!m_Face;
diff --git a/core/fxge/include/fx_font.h b/core/fxge/include/fx_font.h
index 8c9bdb9..9b43f16 100644
--- a/core/fxge/include/fx_font.h
+++ b/core/fxge/include/fx_font.h
@@ -86,7 +86,7 @@
 
   FX_BOOL LoadEmbedded(const uint8_t* data, uint32_t size);
   FXFT_Face GetFace() const { return m_Face; }
-  CFX_SubstFont* GetSubstFont() const { return m_pSubstFont; }
+  CFX_SubstFont* GetSubstFont() const { return m_pSubstFont.get(); }
 
 #ifdef PDF_ENABLE_XFA
   FX_BOOL LoadFile(IFX_FileRead* pFile,
@@ -95,7 +95,9 @@
 
   FX_BOOL LoadClone(const CFX_Font* pFont);
   void SetFace(FXFT_Face face) { m_Face = face; }
-  void SetSubstFont(CFX_SubstFont* subst) { m_pSubstFont = subst; }
+  void SetSubstFont(std::unique_ptr<CFX_SubstFont> subst) {
+    m_pSubstFont = std::move(subst);
+  }
 #endif  // PDF_ENABLE_XFA
 
   CFX_PathData* LoadGlyphPath(uint32_t glyph_index, int dest_width = 0);
@@ -139,8 +141,8 @@
   void DeleteFace();
 
   FXFT_Face m_Face;
-  CFX_SubstFont* m_pSubstFont;
-  uint8_t* m_pFontDataAllocation;
+  std::unique_ptr<CFX_SubstFont> m_pSubstFont;
+  std::vector<uint8_t> m_pFontDataAllocation;
   uint8_t* m_pFontData;
   uint8_t* m_pGsubData;
   uint32_t m_dwSize;
@@ -501,6 +503,7 @@
   CFX_FontCache* m_pFontCache;
   CFX_Font* m_pFont;
 };
+
 #define FX_FONTCACHE_DEFINE(pFontCache, pFont) \
   CFX_AutoFontCache autoFontCache((pFontCache), (pFont))
 class CFX_GlyphBitmap {
@@ -509,6 +512,7 @@
   int m_Left;
   CFX_DIBitmap m_Bitmap;
 };
+
 class CFX_FaceCache {
  public:
   explicit CFX_FaceCache(FXFT_Face face);
diff --git a/xfa/fde/fde_gedevice.cpp b/xfa/fde/fde_gedevice.cpp
index e78ab8d..56f845c 100644
--- a/xfa/fde/fde_gedevice.cpp
+++ b/xfa/fde/fde_gedevice.cpp
@@ -134,12 +134,12 @@
 #if _FXM_PLATFORM_ != _FXM_PLATFORM_WINDOWS_
   uint32_t dwFontStyle = pFont->GetFontStyles();
   CFX_Font FxFont;
-  CFX_SubstFont SubstFxFont;
-  FxFont.SetSubstFont(&SubstFxFont);
-  SubstFxFont.m_Weight = dwFontStyle & FX_FONTSTYLE_Bold ? 700 : 400;
-  SubstFxFont.m_ItalicAngle = dwFontStyle & FX_FONTSTYLE_Italic ? -12 : 0;
-  SubstFxFont.m_WeightCJK = SubstFxFont.m_Weight;
-  SubstFxFont.m_bItalicCJK = !!(dwFontStyle & FX_FONTSTYLE_Italic);
+  CFX_SubstFont* SubstFxFont = new CFX_SubstFont();
+  FxFont.SetSubstFont(std::unique_ptr<CFX_SubstFont>(SubstFxFont));
+  SubstFxFont->m_Weight = dwFontStyle & FX_FONTSTYLE_Bold ? 700 : 400;
+  SubstFxFont->m_ItalicAngle = dwFontStyle & FX_FONTSTYLE_Italic ? -12 : 0;
+  SubstFxFont->m_WeightCJK = SubstFxFont->m_Weight;
+  SubstFxFont->m_bItalicCJK = !!(dwFontStyle & FX_FONTSTYLE_Italic);
 #endif  // _FXM_PLATFORM_ != _FXM_PLATFORM_WINDOWS_
 
   for (int32_t i = 0; i < iCount; ++i) {
@@ -175,7 +175,6 @@
     FX_BOOL bRet = m_pDevice->DrawNormalText(
         iCurCount, pCurCP, &FxFont, pCache, -fFontSize,
         (const CFX_Matrix*)pMatrix, argb, FXTEXT_CLEARTYPE);
-    FxFont.SetSubstFont(nullptr);
     FxFont.SetFace(nullptr);
     return bRet;
 #else
@@ -186,7 +185,6 @@
   }
 
 #if _FXM_PLATFORM_ != _FXM_PLATFORM_WINDOWS_
-  FxFont.SetSubstFont(nullptr);
   FxFont.SetFace(nullptr);
 #endif  // _FXM_PLATFORM_ != _FXM_PLATFORM_WINDOWS_
 
diff --git a/xfa/fgas/font/fgas_gefont.cpp b/xfa/fgas/font/fgas_gefont.cpp
index 576f482..48635ca 100644
--- a/xfa/fgas/font/fgas_gefont.cpp
+++ b/xfa/fgas/font/fgas_gefont.cpp
@@ -109,7 +109,7 @@
   CFX_SubstFont* pSubst = m_pFont->GetSubstFont();
   if (!pSubst) {
     pSubst = new CFX_SubstFont;
-    m_pFont->SetSubstFont(pSubst);
+    m_pFont->SetSubstFont(std::unique_ptr<CFX_SubstFont>(pSubst));
   }
   pSubst->m_Weight =
       (dwFontStyles & FX_FONTSTYLE_Bold) ? FXFONT_FW_BOLD : FXFONT_FW_NORMAL;