OLD | NEW |
---|---|
1 // Copyright 2014 PDFium Authors. All rights reserved. | 1 // Copyright 2014 PDFium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 // Original code copyright 2014 Foxit Software Inc. http://www.foxitsoftware.com | 5 // Original code copyright 2014 Foxit Software Inc. http://www.foxitsoftware.com |
6 | 6 |
7 #include <set> | 7 #include <set> |
8 #include <utility> | 8 #include <utility> |
9 #include <vector> | 9 #include <vector> |
10 | 10 |
11 #include "../../../include/fpdfapi/fpdf_module.h" | 11 #include "../../../include/fpdfapi/fpdf_module.h" |
12 #include "../../../include/fpdfapi/fpdf_page.h" | 12 #include "../../../include/fpdfapi/fpdf_page.h" |
13 #include "../../../include/fpdfapi/fpdf_parser.h" | 13 #include "../../../include/fpdfapi/fpdf_parser.h" |
14 #include "../../../include/fxcrt/fx_safe_types.h" | 14 #include "../../../include/fxcrt/fx_safe_types.h" |
15 #include "../fpdf_page/pageint.h" | 15 #include "../fpdf_page/pageint.h" |
16 #include "parser_int.h" | |
16 | 17 |
17 FX_BOOL IsSignatureDict(const CPDF_Dictionary* pDict) { | 18 FX_BOOL IsSignatureDict(const CPDF_Dictionary* pDict) { |
18 CPDF_Object* pType = pDict->GetElementValue(FX_BSTRC("Type")); | 19 CPDF_Object* pType = pDict->GetElementValue(FX_BSTRC("Type")); |
19 if (!pType) { | 20 if (!pType) { |
20 pType = pDict->GetElementValue(FX_BSTRC("FT")); | 21 pType = pDict->GetElementValue(FX_BSTRC("FT")); |
21 if (!pType) { | 22 if (!pType) { |
22 return FALSE; | 23 return FALSE; |
23 } | 24 } |
24 } | 25 } |
25 if (pType->GetString() == FX_BSTRC("Sig")) { | 26 if (pType->GetString() == FX_BSTRC("Sig")) { |
(...skipping 2777 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2803 } | 2804 } |
2804 buffer[offset++] = ch; | 2805 buffer[offset++] = ch; |
2805 if (offset == size) { | 2806 if (offset == size) { |
2806 break; | 2807 break; |
2807 } | 2808 } |
2808 } | 2809 } |
2809 } | 2810 } |
2810 | 2811 |
2811 class CPDF_DataAvail final : public IPDF_DataAvail { | 2812 class CPDF_DataAvail final : public IPDF_DataAvail { |
2812 public: | 2813 public: |
2813 CPDF_DataAvail(IFX_FileAvail* pFileAvail, IFX_FileRead* pFileRead); | 2814 CPDF_DataAvail(IFX_FileAvail* pFileAvail, |
2815 IFX_FileRead* pFileRead, | |
2816 FX_BOOL bSupportHintTable = FALSE); | |
Lei Zhang
2015/09/22 23:33:43
It would be nice to not have default parameters
jun_fang
2015/09/23 12:26:58
Acknowledged.
| |
2814 ~CPDF_DataAvail() override; | 2817 ~CPDF_DataAvail() override; |
2815 | 2818 |
2816 virtual FX_BOOL IsDocAvail(IFX_DownloadHints* pHints) override; | 2819 virtual FX_BOOL IsDocAvail(IFX_DownloadHints* pHints) override; |
2817 | 2820 |
2818 virtual void SetDocument(CPDF_Document* pDoc) override; | 2821 virtual void SetDocument(CPDF_Document* pDoc) override; |
2819 | 2822 |
2820 virtual FX_BOOL IsPageAvail(int iPage, IFX_DownloadHints* pHints) override; | 2823 virtual FX_BOOL IsPageAvail(int iPage, IFX_DownloadHints* pHints) override; |
2821 | 2824 |
2822 virtual int32_t IsFormAvail(IFX_DownloadHints* pHints) override; | 2825 virtual int32_t IsFormAvail(IFX_DownloadHints* pHints) override; |
2823 | 2826 |
2824 virtual int32_t IsLinearizedPDF() override; | 2827 virtual int32_t IsLinearizedPDF() override; |
2825 | 2828 |
2826 virtual FX_BOOL IsLinearized() override { return m_bLinearized; } | 2829 virtual FX_BOOL IsLinearized() override { return m_bLinearized; } |
2827 | 2830 |
2828 virtual void GetLinearizedMainXRefInfo(FX_FILESIZE* pPos, | 2831 virtual void GetLinearizedMainXRefInfo(FX_FILESIZE* pPos, |
2829 FX_DWORD* pSize) override; | 2832 FX_DWORD* pSize) override; |
2833 int GetPageCount() const; | |
2834 CPDF_Dictionary* GetPage(int index); | |
2830 | 2835 |
2831 protected: | 2836 protected: |
2832 static const int kMaxDataAvailRecursionDepth = 64; | 2837 static const int kMaxDataAvailRecursionDepth = 64; |
2833 static int s_CurrentDataAvailRecursionDepth; | 2838 static int s_CurrentDataAvailRecursionDepth; |
2834 | 2839 |
2835 FX_DWORD GetObjectSize(FX_DWORD objnum, FX_FILESIZE& offset); | 2840 FX_DWORD GetObjectSize(FX_DWORD objnum, FX_FILESIZE& offset); |
2836 FX_BOOL IsObjectsAvail(CFX_PtrArray& obj_array, | 2841 FX_BOOL IsObjectsAvail(CFX_PtrArray& obj_array, |
2837 FX_BOOL bParsePage, | 2842 FX_BOOL bParsePage, |
2838 IFX_DownloadHints* pHints, | 2843 IFX_DownloadHints* pHints, |
2839 CFX_PtrArray& ret_array); | 2844 CFX_PtrArray& ret_array); |
2840 FX_BOOL CheckDocStatus(IFX_DownloadHints* pHints); | 2845 FX_BOOL CheckDocStatus(IFX_DownloadHints* pHints); |
2841 FX_BOOL CheckHeader(IFX_DownloadHints* pHints); | 2846 FX_BOOL CheckHeader(IFX_DownloadHints* pHints); |
2842 FX_BOOL CheckFirstPage(IFX_DownloadHints* pHints); | 2847 FX_BOOL CheckFirstPage(IFX_DownloadHints* pHints); |
2848 FX_BOOL CheckHintTables(IFX_DownloadHints* pHints); | |
2843 FX_BOOL CheckEnd(IFX_DownloadHints* pHints); | 2849 FX_BOOL CheckEnd(IFX_DownloadHints* pHints); |
2844 FX_BOOL CheckCrossRef(IFX_DownloadHints* pHints); | 2850 FX_BOOL CheckCrossRef(IFX_DownloadHints* pHints); |
2845 FX_BOOL CheckCrossRefItem(IFX_DownloadHints* pHints); | 2851 FX_BOOL CheckCrossRefItem(IFX_DownloadHints* pHints); |
2846 FX_BOOL CheckTrailer(IFX_DownloadHints* pHints); | 2852 FX_BOOL CheckTrailer(IFX_DownloadHints* pHints); |
2847 FX_BOOL CheckRoot(IFX_DownloadHints* pHints); | 2853 FX_BOOL CheckRoot(IFX_DownloadHints* pHints); |
2848 FX_BOOL CheckInfo(IFX_DownloadHints* pHints); | 2854 FX_BOOL CheckInfo(IFX_DownloadHints* pHints); |
2849 FX_BOOL CheckPages(IFX_DownloadHints* pHints); | 2855 FX_BOOL CheckPages(IFX_DownloadHints* pHints); |
2850 FX_BOOL CheckPage(IFX_DownloadHints* pHints); | 2856 FX_BOOL CheckPage(IFX_DownloadHints* pHints); |
2851 FX_BOOL CheckResources(IFX_DownloadHints* pHints); | 2857 FX_BOOL CheckResources(IFX_DownloadHints* pHints); |
2852 FX_BOOL CheckAnnots(IFX_DownloadHints* pHints); | 2858 FX_BOOL CheckAnnots(IFX_DownloadHints* pHints); |
2853 FX_BOOL CheckAcroForm(IFX_DownloadHints* pHints); | 2859 FX_BOOL CheckAcroForm(IFX_DownloadHints* pHints); |
2854 FX_BOOL CheckAcroFormSubObject(IFX_DownloadHints* pHints); | 2860 FX_BOOL CheckAcroFormSubObject(IFX_DownloadHints* pHints); |
2855 FX_BOOL CheckTrailerAppend(IFX_DownloadHints* pHints); | 2861 FX_BOOL CheckTrailerAppend(IFX_DownloadHints* pHints); |
2856 FX_BOOL CheckPageStatus(IFX_DownloadHints* pHints); | 2862 FX_BOOL CheckPageStatus(IFX_DownloadHints* pHints); |
2857 FX_BOOL CheckAllCrossRefStream(IFX_DownloadHints* pHints); | 2863 FX_BOOL CheckAllCrossRefStream(IFX_DownloadHints* pHints); |
2858 | 2864 |
2859 int32_t CheckCrossRefStream(IFX_DownloadHints* pHints, | 2865 int32_t CheckCrossRefStream(IFX_DownloadHints* pHints, |
2860 FX_FILESIZE& xref_offset); | 2866 FX_FILESIZE& xref_offset); |
2861 FX_BOOL IsLinearizedFile(uint8_t* pData, FX_DWORD dwLen); | 2867 FX_BOOL IsLinearizedFile(uint8_t* pData, FX_DWORD dwLen); |
2862 void SetStartOffset(FX_FILESIZE dwOffset); | 2868 void SetStartOffset(FX_FILESIZE dwOffset); |
2863 FX_BOOL GetNextToken(CFX_ByteString& token); | 2869 FX_BOOL GetNextToken(CFX_ByteString& token); |
2864 FX_BOOL GetNextChar(uint8_t& ch); | 2870 FX_BOOL GetNextChar(uint8_t& ch); |
2865 CPDF_Object* ParseIndirectObjectAt(FX_FILESIZE pos, FX_DWORD objnum); | 2871 CPDF_Object* ParseIndirectObjectAt(FX_FILESIZE pos, |
2872 FX_DWORD objnum, | |
2873 CPDF_IndirectObjects* pObjList = NULL); | |
2866 CPDF_Object* GetObject(FX_DWORD objnum, | 2874 CPDF_Object* GetObject(FX_DWORD objnum, |
2867 IFX_DownloadHints* pHints, | 2875 IFX_DownloadHints* pHints, |
2868 FX_BOOL* pExistInFile); | 2876 FX_BOOL* pExistInFile); |
2869 FX_BOOL GetPageKids(CPDF_Parser* pParser, CPDF_Object* pPages); | 2877 FX_BOOL GetPageKids(CPDF_Parser* pParser, CPDF_Object* pPages); |
2870 FX_BOOL PreparePageItem(); | 2878 FX_BOOL PreparePageItem(); |
2871 FX_BOOL LoadPages(IFX_DownloadHints* pHints); | 2879 FX_BOOL LoadPages(IFX_DownloadHints* pHints); |
2872 FX_BOOL LoadAllXref(IFX_DownloadHints* pHints); | 2880 FX_BOOL LoadAllXref(IFX_DownloadHints* pHints); |
2873 FX_BOOL LoadAllFile(IFX_DownloadHints* pHints); | 2881 FX_BOOL LoadAllFile(IFX_DownloadHints* pHints); |
2874 FX_BOOL CheckLinearizedData(IFX_DownloadHints* pHints); | 2882 FX_BOOL CheckLinearizedData(IFX_DownloadHints* pHints); |
2875 FX_BOOL CheckFileResources(IFX_DownloadHints* pHints); | 2883 FX_BOOL CheckFileResources(IFX_DownloadHints* pHints); |
(...skipping 10 matching lines...) Expand all Loading... | |
2886 IFX_DownloadHints* pHints); | 2894 IFX_DownloadHints* pHints); |
2887 FX_BOOL CheckUnkownPageNode(FX_DWORD dwPageNo, | 2895 FX_BOOL CheckUnkownPageNode(FX_DWORD dwPageNo, |
2888 CPDF_PageNode* pPageNode, | 2896 CPDF_PageNode* pPageNode, |
2889 IFX_DownloadHints* pHints); | 2897 IFX_DownloadHints* pHints); |
2890 FX_BOOL CheckArrayPageNode(FX_DWORD dwPageNo, | 2898 FX_BOOL CheckArrayPageNode(FX_DWORD dwPageNo, |
2891 CPDF_PageNode* pPageNode, | 2899 CPDF_PageNode* pPageNode, |
2892 IFX_DownloadHints* pHints); | 2900 IFX_DownloadHints* pHints); |
2893 FX_BOOL CheckPageCount(IFX_DownloadHints* pHints); | 2901 FX_BOOL CheckPageCount(IFX_DownloadHints* pHints); |
2894 FX_BOOL IsFirstCheck(int iPage); | 2902 FX_BOOL IsFirstCheck(int iPage); |
2895 void ResetFirstCheck(int iPage); | 2903 void ResetFirstCheck(int iPage); |
2904 FX_BOOL IsDataAvail(FX_FILESIZE offset, | |
2905 FX_DWORD size, | |
2906 IFX_DownloadHints* pHints); | |
2896 | 2907 |
2897 CPDF_Parser m_parser; | 2908 CPDF_Parser m_parser; |
2898 | 2909 |
2899 CPDF_SyntaxParser m_syntaxParser; | 2910 CPDF_SyntaxParser m_syntaxParser; |
2900 | 2911 |
2901 CPDF_Object* m_pRoot; | 2912 CPDF_Object* m_pRoot; |
2902 | 2913 |
2903 FX_DWORD m_dwRootObjNum; | 2914 FX_DWORD m_dwRootObjNum; |
2904 | 2915 |
2905 FX_DWORD m_dwInfoObjNum; | 2916 FX_DWORD m_dwInfoObjNum; |
(...skipping 93 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2999 FX_FILESIZE m_dwPrevXRefOffset; | 3010 FX_FILESIZE m_dwPrevXRefOffset; |
3000 | 3011 |
3001 FX_BOOL m_bTotalLoadPageTree; | 3012 FX_BOOL m_bTotalLoadPageTree; |
3002 | 3013 |
3003 FX_BOOL m_bCurPageDictLoadOK; | 3014 FX_BOOL m_bCurPageDictLoadOK; |
3004 | 3015 |
3005 CPDF_PageNode m_pageNodes; | 3016 CPDF_PageNode m_pageNodes; |
3006 | 3017 |
3007 std::set<FX_DWORD> m_pageMapCheckState; | 3018 std::set<FX_DWORD> m_pageMapCheckState; |
3008 std::set<FX_DWORD> m_pagesLoadState; | 3019 std::set<FX_DWORD> m_pagesLoadState; |
3020 | |
3021 CPDF_HintTables* m_pHintTables; | |
3022 FX_BOOL m_bSupportHintTable; | |
3023 | |
3024 public: | |
3025 friend class CPDF_HintTables; | |
Lei Zhang
2015/09/22 23:33:43
just put this in the public section
jun_fang
2015/09/23 12:26:58
Acknowledged.
| |
3009 }; | 3026 }; |
3010 | 3027 |
3011 IPDF_DataAvail::IPDF_DataAvail(IFX_FileAvail* pFileAvail, | 3028 IPDF_DataAvail::IPDF_DataAvail(IFX_FileAvail* pFileAvail, |
3012 IFX_FileRead* pFileRead) | 3029 IFX_FileRead* pFileRead) |
3013 : m_pFileAvail(pFileAvail), m_pFileRead(pFileRead) {} | 3030 : m_pFileAvail(pFileAvail), m_pFileRead(pFileRead) { |
3031 } | |
3014 | 3032 |
3015 // static | 3033 // static |
3016 IPDF_DataAvail* IPDF_DataAvail::Create(IFX_FileAvail* pFileAvail, | 3034 IPDF_DataAvail* IPDF_DataAvail::Create(IFX_FileAvail* pFileAvail, |
3017 IFX_FileRead* pFileRead) { | 3035 IFX_FileRead* pFileRead) { |
3018 return new CPDF_DataAvail(pFileAvail, pFileRead); | 3036 return new CPDF_DataAvail(pFileAvail, pFileRead); |
3019 } | 3037 } |
3020 | 3038 |
3021 // static | 3039 // static |
3022 int CPDF_DataAvail::s_CurrentDataAvailRecursionDepth = 0; | 3040 int CPDF_DataAvail::s_CurrentDataAvailRecursionDepth = 0; |
3023 | 3041 |
3024 CPDF_DataAvail::CPDF_DataAvail(IFX_FileAvail* pFileAvail, | 3042 CPDF_DataAvail::CPDF_DataAvail(IFX_FileAvail* pFileAvail, |
3025 IFX_FileRead* pFileRead) | 3043 IFX_FileRead* pFileRead, |
3044 FX_BOOL bSupportHintTable) | |
3026 : IPDF_DataAvail(pFileAvail, pFileRead) { | 3045 : IPDF_DataAvail(pFileAvail, pFileRead) { |
3027 m_Pos = 0; | 3046 m_Pos = 0; |
3028 m_dwFileLen = 0; | 3047 m_dwFileLen = 0; |
3029 if (m_pFileRead) { | 3048 if (m_pFileRead) { |
3030 m_dwFileLen = (FX_DWORD)m_pFileRead->GetSize(); | 3049 m_dwFileLen = (FX_DWORD)m_pFileRead->GetSize(); |
3031 } | 3050 } |
3032 m_dwCurrentOffset = 0; | 3051 m_dwCurrentOffset = 0; |
3033 m_WordSize = 0; | 3052 m_WordSize = 0; |
3034 m_dwXRefOffset = 0; | 3053 m_dwXRefOffset = 0; |
3035 m_bufferOffset = 0; | 3054 m_bufferOffset = 0; |
(...skipping 25 matching lines...) Expand all Loading... | |
3061 m_pTrailer = NULL; | 3080 m_pTrailer = NULL; |
3062 m_pCurrentParser = NULL; | 3081 m_pCurrentParser = NULL; |
3063 m_pAcroForm = NULL; | 3082 m_pAcroForm = NULL; |
3064 m_pPageDict = NULL; | 3083 m_pPageDict = NULL; |
3065 m_pPageResource = NULL; | 3084 m_pPageResource = NULL; |
3066 m_docStatus = PDF_DATAAVAIL_HEADER; | 3085 m_docStatus = PDF_DATAAVAIL_HEADER; |
3067 m_parser.m_bOwnFileRead = FALSE; | 3086 m_parser.m_bOwnFileRead = FALSE; |
3068 m_bTotalLoadPageTree = FALSE; | 3087 m_bTotalLoadPageTree = FALSE; |
3069 m_bCurPageDictLoadOK = FALSE; | 3088 m_bCurPageDictLoadOK = FALSE; |
3070 m_bLinearedDataOK = FALSE; | 3089 m_bLinearedDataOK = FALSE; |
3090 m_bSupportHintTable = bSupportHintTable; | |
Tom Sepez
2015/09/22 19:17:59
Why did we lose this initialization? It needs to b
jun_fang
2015/09/23 12:26:58
Good catch! I tried to use unique_ptr first but di
| |
3071 } | 3091 } |
3072 CPDF_DataAvail::~CPDF_DataAvail() { | 3092 CPDF_DataAvail::~CPDF_DataAvail() { |
3073 if (m_pLinearized) { | 3093 if (m_pLinearized) { |
3074 m_pLinearized->Release(); | 3094 m_pLinearized->Release(); |
3075 } | 3095 } |
3076 if (m_pRoot) { | 3096 if (m_pRoot) { |
3077 m_pRoot->Release(); | 3097 m_pRoot->Release(); |
3078 } | 3098 } |
3079 if (m_pTrailer) { | 3099 if (m_pTrailer) { |
3080 m_pTrailer->Release(); | 3100 m_pTrailer->Release(); |
3081 } | 3101 } |
3082 int32_t i = 0; | 3102 delete m_pHintTables; |
Tom Sepez
2015/09/22 19:17:59
remove when unique_ptr.
jun_fang
2015/09/23 12:26:58
Acknowledged.
| |
3083 int32_t iSize = m_arrayAcroforms.GetSize(); | 3103 int32_t iSize = m_arrayAcroforms.GetSize(); |
3084 for (i = 0; i < iSize; ++i) { | 3104 for (int i = 0; i < iSize; ++i) { |
3085 ((CPDF_Object*)m_arrayAcroforms.GetAt(i))->Release(); | 3105 ((CPDF_Object*)m_arrayAcroforms.GetAt(i))->Release(); |
3086 } | 3106 } |
3087 } | 3107 } |
3088 void CPDF_DataAvail::SetDocument(CPDF_Document* pDoc) { | 3108 void CPDF_DataAvail::SetDocument(CPDF_Document* pDoc) { |
3089 m_pDocument = pDoc; | 3109 m_pDocument = pDoc; |
3090 } | 3110 } |
3091 FX_DWORD CPDF_DataAvail::GetObjectSize(FX_DWORD objnum, FX_FILESIZE& offset) { | 3111 FX_DWORD CPDF_DataAvail::GetObjectSize(FX_DWORD objnum, FX_FILESIZE& offset) { |
3092 CPDF_Parser* pParser = (CPDF_Parser*)(m_pDocument->GetParser()); | 3112 CPDF_Parser* pParser = (CPDF_Parser*)(m_pDocument->GetParser()); |
3093 if (pParser == NULL) { | 3113 if (pParser == NULL) { |
3094 return 0; | 3114 return 0; |
(...skipping 61 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
3156 value = pDict->GetNextElement(pos, key); | 3176 value = pDict->GetNextElement(pos, key); |
3157 if (key != "Parent") { | 3177 if (key != "Parent") { |
3158 new_obj_array.Add(value); | 3178 new_obj_array.Add(value); |
3159 } | 3179 } |
3160 } | 3180 } |
3161 } break; | 3181 } break; |
3162 case PDFOBJ_REFERENCE: { | 3182 case PDFOBJ_REFERENCE: { |
3163 CPDF_Reference* pRef = (CPDF_Reference*)pObj; | 3183 CPDF_Reference* pRef = (CPDF_Reference*)pObj; |
3164 FX_DWORD dwNum = pRef->GetRefObjNum(); | 3184 FX_DWORD dwNum = pRef->GetRefObjNum(); |
3165 FX_FILESIZE offset; | 3185 FX_FILESIZE offset; |
3166 FX_DWORD original_size = GetObjectSize(dwNum, offset); | 3186 FX_DWORD size = GetObjectSize(dwNum, offset); |
3167 pdfium::base::CheckedNumeric<FX_DWORD> size = original_size; | 3187 if (size == 0 || offset < 0 || offset >= m_dwFileLen) { |
3168 if (size.ValueOrDefault(0) == 0 || offset < 0 || | |
3169 offset >= m_dwFileLen) { | |
3170 break; | 3188 break; |
3171 } | 3189 } |
3172 | 3190 if (!IsDataAvail(offset, size, pHints)) { |
Lei Zhang
2015/09/22 23:33:43
In the old code, if IsValid() returns false, we br
jun_fang
2015/09/23 12:26:58
Good catch. Will update the code in IsDataAvail().
| |
3173 size += offset; | |
3174 size += 512; | |
3175 if (!size.IsValid()) { | |
3176 break; | |
3177 } | |
3178 if (size.ValueOrDie() > m_dwFileLen) { | |
3179 size = m_dwFileLen - offset; | |
3180 } else { | |
3181 size = original_size + 512; | |
3182 } | |
3183 if (!size.IsValid()) { | |
3184 break; | |
3185 } | |
3186 if (!m_pFileAvail->IsDataAvail(offset, size.ValueOrDie())) { | |
3187 pHints->AddSegment(offset, size.ValueOrDie()); | |
3188 ret_array.Add(pObj); | 3191 ret_array.Add(pObj); |
3189 count++; | 3192 count++; |
3190 } else if (!m_objnum_array.Find(dwNum)) { | 3193 } else if (!m_objnum_array.Find(dwNum)) { |
3191 m_objnum_array.AddObjNum(dwNum); | 3194 m_objnum_array.AddObjNum(dwNum); |
3192 CPDF_Object* pReferred = | 3195 CPDF_Object* pReferred = |
3193 m_pDocument->GetIndirectObject(pRef->GetRefObjNum(), NULL); | 3196 m_pDocument->GetIndirectObject(pRef->GetRefObjNum(), NULL); |
3194 if (pReferred) { | 3197 if (pReferred) { |
3195 new_obj_array.Add(pReferred); | 3198 new_obj_array.Add(pReferred); |
3196 } | 3199 } |
3197 } | 3200 } |
(...skipping 79 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
3277 m_docStatus = PDF_DATAAVAIL_PAGETREE; | 3280 m_docStatus = PDF_DATAAVAIL_PAGETREE; |
3278 return TRUE; | 3281 return TRUE; |
3279 } | 3282 } |
3280 FX_BOOL CPDF_DataAvail::CheckDocStatus(IFX_DownloadHints* pHints) { | 3283 FX_BOOL CPDF_DataAvail::CheckDocStatus(IFX_DownloadHints* pHints) { |
3281 switch (m_docStatus) { | 3284 switch (m_docStatus) { |
3282 case PDF_DATAAVAIL_HEADER: | 3285 case PDF_DATAAVAIL_HEADER: |
3283 return CheckHeader(pHints); | 3286 return CheckHeader(pHints); |
3284 case PDF_DATAAVAIL_FIRSTPAGE: | 3287 case PDF_DATAAVAIL_FIRSTPAGE: |
3285 case PDF_DATAAVAIL_FIRSTPAGE_PREPARE: | 3288 case PDF_DATAAVAIL_FIRSTPAGE_PREPARE: |
3286 return CheckFirstPage(pHints); | 3289 return CheckFirstPage(pHints); |
3290 case PDF_DATAAVAIL_HINTTABLE: | |
3291 return CheckHintTables(pHints); | |
3287 case PDF_DATAAVAIL_END: | 3292 case PDF_DATAAVAIL_END: |
3288 return CheckEnd(pHints); | 3293 return CheckEnd(pHints); |
3289 case PDF_DATAAVAIL_CROSSREF: | 3294 case PDF_DATAAVAIL_CROSSREF: |
3290 return CheckCrossRef(pHints); | 3295 return CheckCrossRef(pHints); |
3291 case PDF_DATAAVAIL_CROSSREF_ITEM: | 3296 case PDF_DATAAVAIL_CROSSREF_ITEM: |
3292 return CheckCrossRefItem(pHints); | 3297 return CheckCrossRefItem(pHints); |
3293 case PDF_DATAAVAIL_CROSSREF_STREAM: | 3298 case PDF_DATAAVAIL_CROSSREF_STREAM: |
3294 return CheckAllCrossRefStream(pHints); | 3299 return CheckAllCrossRefStream(pHints); |
3295 case PDF_DATAAVAIL_TRAILER: | 3300 case PDF_DATAAVAIL_TRAILER: |
3296 return CheckTrailer(pHints); | 3301 return CheckTrailer(pHints); |
(...skipping 64 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
3361 _CompareFileSize); | 3366 _CompareFileSize); |
3362 m_dwRootObjNum = m_parser.GetRootObjNum(); | 3367 m_dwRootObjNum = m_parser.GetRootObjNum(); |
3363 m_dwInfoObjNum = m_parser.GetInfoObjNum(); | 3368 m_dwInfoObjNum = m_parser.GetInfoObjNum(); |
3364 m_pCurrentParser = &m_parser; | 3369 m_pCurrentParser = &m_parser; |
3365 m_docStatus = PDF_DATAAVAIL_ROOT; | 3370 m_docStatus = PDF_DATAAVAIL_ROOT; |
3366 return TRUE; | 3371 return TRUE; |
3367 } | 3372 } |
3368 CPDF_Object* CPDF_DataAvail::GetObject(FX_DWORD objnum, | 3373 CPDF_Object* CPDF_DataAvail::GetObject(FX_DWORD objnum, |
3369 IFX_DownloadHints* pHints, | 3374 IFX_DownloadHints* pHints, |
3370 FX_BOOL* pExistInFile) { | 3375 FX_BOOL* pExistInFile) { |
3371 CPDF_Object* pRet = NULL; | 3376 CPDF_Object* pRet = nullptr; |
3372 FX_DWORD original_size = 0; | 3377 FX_DWORD size = 0; |
3373 FX_FILESIZE offset = 0; | 3378 FX_FILESIZE offset = 0; |
3374 CPDF_Parser* pParser = NULL; | 3379 CPDF_Parser* pParser = nullptr; |
3375 | 3380 if (pExistInFile) |
3376 if (pExistInFile) { | |
3377 *pExistInFile = TRUE; | 3381 *pExistInFile = TRUE; |
3378 } | |
3379 | 3382 |
3380 if (m_pDocument == NULL) { | 3383 if (m_pDocument == NULL) { |
3381 original_size = (FX_DWORD)m_parser.GetObjectSize(objnum); | 3384 size = (FX_DWORD)m_parser.GetObjectSize(objnum); |
3382 offset = m_parser.GetObjectOffset(objnum); | 3385 offset = m_parser.GetObjectOffset(objnum); |
3383 pParser = &m_parser; | 3386 pParser = &m_parser; |
3384 } else { | 3387 } else { |
3385 original_size = GetObjectSize(objnum, offset); | 3388 size = GetObjectSize(objnum, offset); |
3386 pParser = (CPDF_Parser*)(m_pDocument->GetParser()); | 3389 pParser = (CPDF_Parser*)(m_pDocument->GetParser()); |
3387 } | 3390 } |
3388 | 3391 if (!IsDataAvail(offset, size, pHints)) { |
3389 pdfium::base::CheckedNumeric<FX_DWORD> size = original_size; | 3392 return nullptr; |
3390 if (size.ValueOrDefault(0) == 0 || offset < 0 || offset >= m_dwFileLen) { | 3393 } |
3391 if (pExistInFile) | |
3392 *pExistInFile = FALSE; | |
3393 | |
3394 return NULL; | |
3395 } | |
3396 | |
3397 size += offset; | |
3398 size += 512; | |
3399 if (!size.IsValid()) { | |
3400 return NULL; | |
3401 } | |
3402 | |
3403 if (size.ValueOrDie() > m_dwFileLen) { | |
3404 size = m_dwFileLen - offset; | |
3405 } else { | |
3406 size = original_size + 512; | |
3407 } | |
3408 | |
3409 if (!size.IsValid()) { | |
3410 return NULL; | |
3411 } | |
3412 | |
3413 if (!m_pFileAvail->IsDataAvail(offset, size.ValueOrDie())) { | |
3414 pHints->AddSegment(offset, size.ValueOrDie()); | |
3415 return NULL; | |
3416 } | |
3417 | |
3418 if (pParser) { | 3394 if (pParser) { |
3419 pRet = pParser->ParseIndirectObject(NULL, objnum, NULL); | 3395 pRet = pParser->ParseIndirectObject(NULL, objnum, NULL); |
3420 } | 3396 } |
3421 | |
3422 if (!pRet && pExistInFile) { | 3397 if (!pRet && pExistInFile) { |
3423 *pExistInFile = FALSE; | 3398 *pExistInFile = FALSE; |
3424 } | 3399 } |
3425 | |
3426 return pRet; | 3400 return pRet; |
3427 } | 3401 } |
3428 | |
3429 FX_BOOL CPDF_DataAvail::CheckInfo(IFX_DownloadHints* pHints) { | 3402 FX_BOOL CPDF_DataAvail::CheckInfo(IFX_DownloadHints* pHints) { |
3430 FX_BOOL bExist = FALSE; | 3403 FX_BOOL bExist = FALSE; |
3431 CPDF_Object* pInfo = GetObject(m_dwInfoObjNum, pHints, &bExist); | 3404 CPDF_Object* pInfo = GetObject(m_dwInfoObjNum, pHints, &bExist); |
3432 if (!bExist) { | 3405 if (!bExist) { |
3433 if (m_bHaveAcroForm) { | 3406 if (m_bHaveAcroForm) { |
3434 m_docStatus = PDF_DATAAVAIL_ACROFORM; | 3407 m_docStatus = PDF_DATAAVAIL_ACROFORM; |
3435 } else { | 3408 } else { |
3436 m_docStatus = PDF_DATAAVAIL_PAGETREE; | 3409 m_docStatus = PDF_DATAAVAIL_PAGETREE; |
3437 } | 3410 } |
3438 return TRUE; | 3411 return TRUE; |
(...skipping 269 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
3708 FX_FILESIZE offset = m_dwLastXRefOffset; | 3681 FX_FILESIZE offset = m_dwLastXRefOffset; |
3709 if (dwSize < 512 && dwFileLen > 512) { | 3682 if (dwSize < 512 && dwFileLen > 512) { |
3710 dwSize = 512; | 3683 dwSize = 512; |
3711 offset = dwFileLen - 512; | 3684 offset = dwFileLen - 512; |
3712 } | 3685 } |
3713 pHints->AddSegment(offset, dwSize); | 3686 pHints->AddSegment(offset, dwSize); |
3714 } | 3687 } |
3715 } else { | 3688 } else { |
3716 m_docStatus = PDF_DATAAVAIL_FIRSTPAGE_PREPARE; | 3689 m_docStatus = PDF_DATAAVAIL_FIRSTPAGE_PREPARE; |
3717 } | 3690 } |
3718 if (!bNeedDownLoad && m_docStatus == PDF_DATAAVAIL_FIRSTPAGE_PREPARE) { | 3691 if (bNeedDownLoad || m_docStatus != PDF_DATAAVAIL_FIRSTPAGE_PREPARE) { |
3692 m_docStatus = PDF_DATAAVAIL_FIRSTPAGE_PREPARE; | |
3693 return FALSE; | |
3694 } | |
3695 m_docStatus = | |
3696 m_bSupportHintTable ? PDF_DATAAVAIL_HINTTABLE : PDF_DATAAVAIL_DONE; | |
3697 return TRUE; | |
3698 } | |
3699 FX_BOOL CPDF_DataAvail::IsDataAvail(FX_FILESIZE offset, | |
3700 FX_DWORD size, | |
3701 IFX_DownloadHints* pHints) { | |
3702 if (!pHints || offset > m_dwFileLen) { | |
3703 return TRUE; | |
3704 } | |
3705 FX_SAFE_DWORD safeSize = pdfium::base::checked_cast<FX_DWORD>(offset); | |
3706 safeSize += size; | |
3707 safeSize += 512; | |
3708 if (!safeSize.IsValid()) { | |
3709 return TRUE; | |
3710 } | |
3711 if (safeSize.ValueOrDie() > m_dwFileLen) { | |
3712 size = m_dwFileLen - offset; | |
3713 } else { | |
3714 size += 512; | |
3715 } | |
3716 if (!m_pFileAvail->IsDataAvail(offset, size)) { | |
3717 pHints->AddSegment(offset, size); | |
3718 return FALSE; | |
3719 } | |
3720 return TRUE; | |
3721 } | |
3722 FX_BOOL CPDF_DataAvail::CheckHintTables(IFX_DownloadHints* pHints) { | |
3723 CPDF_Dictionary* pDict = m_pLinearized->GetDict(); | |
3724 if (!pDict || !pHints) { | |
3725 return TRUE; | |
3726 } | |
3727 if (!pDict->KeyExist(FX_BSTRC("H")) || !pDict->KeyExist(FX_BSTRC("O")) || | |
3728 !pDict->KeyExist(FX_BSTRC("N"))) { | |
3719 m_docStatus = PDF_DATAAVAIL_DONE; | 3729 m_docStatus = PDF_DATAAVAIL_DONE; |
3720 return TRUE; | 3730 return TRUE; |
3721 } | 3731 } |
3722 m_docStatus = PDF_DATAAVAIL_FIRSTPAGE_PREPARE; | 3732 int nPageCount = pDict->GetElementValue(FX_BSTRC("N"))->GetInteger(); |
3723 return FALSE; | 3733 if (nPageCount <= 1) { |
3724 } | 3734 m_docStatus = PDF_DATAAVAIL_DONE; |
3725 CPDF_Object* CPDF_DataAvail::ParseIndirectObjectAt(FX_FILESIZE pos, | 3735 return TRUE; |
3726 FX_DWORD objnum) { | 3736 } |
3737 CPDF_Array* pHintStreamRange = pDict->GetArray(FX_BSTRC("H")); | |
3738 FX_FILESIZE szHSStart = | |
3739 pHintStreamRange->GetElementValue(0) | |
3740 ? pHintStreamRange->GetElementValue(0)->GetInteger() | |
3741 : 0; | |
3742 FX_FILESIZE szHSLength = | |
3743 pHintStreamRange->GetElementValue(1) | |
3744 ? pHintStreamRange->GetElementValue(1)->GetInteger() | |
3745 : 0; | |
3746 if (szHSStart < 0 || szHSLength <= 0) { | |
3747 m_docStatus = PDF_DATAAVAIL_DONE; | |
3748 return TRUE; | |
3749 } | |
3750 if (!IsDataAvail(szHSStart, szHSLength, pHints)) { | |
3751 return FALSE; | |
3752 } | |
3753 m_syntaxParser.InitParser(m_pFileRead, m_dwHeaderOffset); | |
3754 nonstd::unique_ptr<CPDF_HintTables> pHintTables( | |
3755 new CPDF_HintTables(this, pDict)); | |
3756 CPDF_Stream* pHintStream = (CPDF_Stream*)ParseIndirectObjectAt(szHSStart, 0); | |
3757 if (!pHintStream || pHintStream->GetType() != PDFOBJ_STREAM) { | |
3758 return FALSE; | |
3759 } | |
3760 if (pHintTables && !pHintTables->LoadHintStream(pHintStream)) { | |
3761 return FALSE; | |
3762 } | |
3763 m_pHintTables = pHintTables.get(); | |
Tom Sepez
2015/09/22 19:17:59
You need to call release(), not get() here, otherw
jun_fang
2015/09/23 12:26:58
Acknowledged.
| |
3764 m_docStatus = PDF_DATAAVAIL_DONE; | |
3765 return TRUE; | |
3766 } | |
3767 CPDF_Object* CPDF_DataAvail::ParseIndirectObjectAt( | |
3768 FX_FILESIZE pos, | |
3769 FX_DWORD objnum, | |
3770 CPDF_IndirectObjects* pObjList) { | |
3727 FX_FILESIZE SavedPos = m_syntaxParser.SavePos(); | 3771 FX_FILESIZE SavedPos = m_syntaxParser.SavePos(); |
3728 m_syntaxParser.RestorePos(pos); | 3772 m_syntaxParser.RestorePos(pos); |
3729 FX_BOOL bIsNumber; | 3773 FX_BOOL bIsNumber; |
3730 CFX_ByteString word = m_syntaxParser.GetNextWord(bIsNumber); | 3774 CFX_ByteString word = m_syntaxParser.GetNextWord(bIsNumber); |
3731 if (!bIsNumber) { | 3775 if (!bIsNumber) { |
3732 return NULL; | 3776 return NULL; |
3733 } | 3777 } |
3734 FX_DWORD parser_objnum = FXSYS_atoi(word); | 3778 FX_DWORD parser_objnum = FXSYS_atoi(word); |
3735 if (objnum && parser_objnum != objnum) { | 3779 if (objnum && parser_objnum != objnum) { |
3736 return NULL; | 3780 return NULL; |
3737 } | 3781 } |
3738 word = m_syntaxParser.GetNextWord(bIsNumber); | 3782 word = m_syntaxParser.GetNextWord(bIsNumber); |
3739 if (!bIsNumber) { | 3783 if (!bIsNumber) { |
3740 return NULL; | 3784 return NULL; |
3741 } | 3785 } |
3742 FX_DWORD gennum = FXSYS_atoi(word); | 3786 FX_DWORD gennum = FXSYS_atoi(word); |
3743 if (m_syntaxParser.GetKeyword() != FX_BSTRC("obj")) { | 3787 if (m_syntaxParser.GetKeyword() != FX_BSTRC("obj")) { |
3744 m_syntaxParser.RestorePos(SavedPos); | 3788 m_syntaxParser.RestorePos(SavedPos); |
3745 return NULL; | 3789 return NULL; |
3746 } | 3790 } |
3747 CPDF_Object* pObj = m_syntaxParser.GetObject(NULL, objnum, gennum, 0); | 3791 CPDF_Object* pObj = |
3792 m_syntaxParser.GetObject(pObjList, parser_objnum, gennum, 0); | |
3748 m_syntaxParser.RestorePos(SavedPos); | 3793 m_syntaxParser.RestorePos(SavedPos); |
3749 return pObj; | 3794 return pObj; |
3750 } | 3795 } |
3751 int32_t CPDF_DataAvail::IsLinearizedPDF() { | 3796 int32_t CPDF_DataAvail::IsLinearizedPDF() { |
3752 FX_DWORD req_size = 1024; | 3797 FX_DWORD req_size = 1024; |
3753 if (!m_pFileAvail->IsDataAvail(0, req_size)) { | 3798 if (!m_pFileAvail->IsDataAvail(0, req_size)) { |
3754 return PDF_UNKNOW_LINEARIZED; | 3799 return PDF_UNKNOW_LINEARIZED; |
3755 } | 3800 } |
3756 if (!m_pFileRead) { | 3801 if (!m_pFileRead) { |
3757 return PDF_NOT_LINEARIZED; | 3802 return PDF_NOT_LINEARIZED; |
(...skipping 737 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
4495 return TRUE; | 4540 return TRUE; |
4496 } | 4541 } |
4497 if (m_bLinearized) { | 4542 if (m_bLinearized) { |
4498 if ((FX_DWORD)iPage == m_dwFirstPageNo) { | 4543 if ((FX_DWORD)iPage == m_dwFirstPageNo) { |
4499 m_pagesLoadState.insert(iPage); | 4544 m_pagesLoadState.insert(iPage); |
4500 return TRUE; | 4545 return TRUE; |
4501 } | 4546 } |
4502 if (!CheckLinearizedData(pHints)) { | 4547 if (!CheckLinearizedData(pHints)) { |
4503 return FALSE; | 4548 return FALSE; |
4504 } | 4549 } |
4550 if (m_pHintTables) { | |
4551 return m_pHintTables->CheckPage(iPage, pHints); | |
4552 } | |
4505 if (m_bMainXRefLoadedOK) { | 4553 if (m_bMainXRefLoadedOK) { |
4506 if (m_bTotalLoadPageTree) { | 4554 if (m_bTotalLoadPageTree) { |
4507 if (!LoadPages(pHints)) { | 4555 if (!LoadPages(pHints)) { |
4508 return FALSE; | 4556 return FALSE; |
4509 } | 4557 } |
4510 } else { | 4558 } else { |
4511 if (!m_bCurPageDictLoadOK && !CheckPage(iPage, pHints)) { | 4559 if (!m_bCurPageDictLoadOK && !CheckPage(iPage, pHints)) { |
4512 return FALSE; | 4560 return FALSE; |
4513 } | 4561 } |
4514 } | 4562 } |
(...skipping 100 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
4615 } | 4663 } |
4616 void CPDF_DataAvail::GetLinearizedMainXRefInfo(FX_FILESIZE* pPos, | 4664 void CPDF_DataAvail::GetLinearizedMainXRefInfo(FX_FILESIZE* pPos, |
4617 FX_DWORD* pSize) { | 4665 FX_DWORD* pSize) { |
4618 if (pPos) { | 4666 if (pPos) { |
4619 *pPos = m_dwLastXRefOffset; | 4667 *pPos = m_dwLastXRefOffset; |
4620 } | 4668 } |
4621 if (pSize) { | 4669 if (pSize) { |
4622 *pSize = (FX_DWORD)(m_dwFileLen - m_dwLastXRefOffset); | 4670 *pSize = (FX_DWORD)(m_dwFileLen - m_dwLastXRefOffset); |
4623 } | 4671 } |
4624 } | 4672 } |
4673 int CPDF_DataAvail::GetPageCount() const { | |
4674 if (!m_pDocument && !m_pLinearized) { | |
4675 return 0; | |
4676 } | |
4677 if (m_pLinearized) { | |
4678 CPDF_Dictionary* pDict = m_pLinearized->GetDict(); | |
4679 CPDF_Object* pObj = pDict ? pDict->GetElementValue(FX_BSTRC("N")) : nullptr; | |
4680 return pObj ? pObj->GetInteger() : 0; | |
4681 } | |
4682 return m_pDocument->GetPageCount(); | |
4683 } | |
4684 CPDF_Dictionary* CPDF_DataAvail::GetPage(int index) { | |
4685 if (!m_pDocument || index < 0 || index >= this->GetPageCount()) { | |
4686 return nullptr; | |
4687 } | |
4688 if (m_pLinearized) { | |
4689 CPDF_Dictionary* pDict = m_pLinearized->GetDict(); | |
4690 CPDF_Object* pObj = pDict ? pDict->GetElementValue(FX_BSTRC("P")) : nullptr; | |
4691 int pageNum = pObj ? pObj->GetInteger() : 0; | |
4692 if (m_pHintTables && index != pageNum) { | |
4693 FX_FILESIZE szPageStartPos = 0; | |
4694 FX_FILESIZE szPageLength = 0; | |
4695 FX_DWORD dwObjNum = 0; | |
4696 FX_BOOL bPagePosGot = m_pHintTables->GetPagePos(index, szPageStartPos, | |
4697 szPageLength, dwObjNum); | |
4698 if (!bPagePosGot) { | |
4699 return nullptr; | |
4700 } | |
4701 m_syntaxParser.InitParser(m_pFileRead, (FX_DWORD)szPageStartPos); | |
4702 CPDF_Object* pPageDict = ParseIndirectObjectAt(0, dwObjNum, m_pDocument); | |
4703 if (!pPageDict) { | |
4704 return nullptr; | |
4705 } | |
4706 m_pDocument->InsertIndirectObject(dwObjNum, pPageDict); | |
4707 return pPageDict->GetDict(); | |
4708 } | |
4709 } | |
4710 return m_pDocument->GetPage(index); | |
4711 } | |
4625 int32_t CPDF_DataAvail::IsFormAvail(IFX_DownloadHints* pHints) { | 4712 int32_t CPDF_DataAvail::IsFormAvail(IFX_DownloadHints* pHints) { |
4626 if (!m_pDocument) { | 4713 if (!m_pDocument) { |
4627 return PDFFORM_AVAIL; | 4714 return PDFFORM_AVAIL; |
4628 } | 4715 } |
4629 if (!m_bLinearizedFormParamLoad) { | 4716 if (!m_bLinearizedFormParamLoad) { |
4630 CPDF_Dictionary* pRoot = m_pDocument->GetRoot(); | 4717 CPDF_Dictionary* pRoot = m_pDocument->GetRoot(); |
4631 if (!pRoot) { | 4718 if (!pRoot) { |
4632 return PDFFORM_AVAIL; | 4719 return PDFFORM_AVAIL; |
4633 } | 4720 } |
4634 CPDF_Object* pAcroForm = pRoot->GetElement(FX_BSTRC("AcroForm")); | 4721 CPDF_Object* pAcroForm = pRoot->GetElement(FX_BSTRC("AcroForm")); |
(...skipping 47 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
4682 return FALSE; | 4769 return FALSE; |
4683 } | 4770 } |
4684 CPDF_PageNode::~CPDF_PageNode() { | 4771 CPDF_PageNode::~CPDF_PageNode() { |
4685 int32_t iSize = m_childNode.GetSize(); | 4772 int32_t iSize = m_childNode.GetSize(); |
4686 for (int32_t i = 0; i < iSize; ++i) { | 4773 for (int32_t i = 0; i < iSize; ++i) { |
4687 CPDF_PageNode* pNode = (CPDF_PageNode*)m_childNode[i]; | 4774 CPDF_PageNode* pNode = (CPDF_PageNode*)m_childNode[i]; |
4688 delete pNode; | 4775 delete pNode; |
4689 } | 4776 } |
4690 m_childNode.RemoveAll(); | 4777 m_childNode.RemoveAll(); |
4691 } | 4778 } |
4779 CPDF_HintTables::~CPDF_HintTables() { | |
4780 m_nFirstPageSharedObjs = 0; | |
4781 m_szFirstPageObjOffset = 0; | |
4782 m_dwDeltaNObjsArray.RemoveAll(); | |
4783 m_dwNSharedObjsArray.RemoveAll(); | |
4784 m_dwSharedObjNumArray.RemoveAll(); | |
4785 m_dwIdentifierArray.RemoveAll(); | |
4786 m_szPageOffsetArray.RemoveAll(); | |
4787 m_szSharedObjOffsetArray.RemoveAll(); | |
4788 } | |
4789 FX_DWORD CPDF_HintTables::GetItemLength(int index, | |
4790 const CFX_FileSizeArray& szArray) { | |
4791 if (index < 0 || index > szArray.GetSize() - 2) | |
4792 return 0; | |
4793 return szArray[index + 1] - szArray[index]; | |
4794 } | |
4795 FX_BOOL CPDF_HintTables::ReadPageHintTable(CFX_BitStream& h) { | |
Lei Zhang
2015/09/22 23:33:43
Change this to a pointer, i.e. no non-const refere
jun_fang
2015/09/23 12:26:58
Acknowledged.
| |
4796 int nStreamOffset = ReadPrimaryHintStreamOffset(h); | |
4797 int nStreamLen = ReadPrimaryHintStreamLength(h); | |
4798 if (nStreamOffset < 0 || nStreamLen < 1) | |
4799 return FALSE; | |
4800 // Item 1: The least number of objects in a page. | |
4801 FX_DWORD dwObjLeastNum = h.GetBits(32); | |
4802 // Item 2: The location of the first page's page object. | |
4803 FX_DWORD dwFirstObjLoc = h.GetBits(32); | |
4804 if (dwFirstObjLoc > nStreamOffset) { | |
4805 FX_SAFE_DWORD safeLoc = pdfium::base::checked_cast<FX_DWORD>(nStreamLen); | |
4806 safeLoc += dwFirstObjLoc; | |
4807 if (!safeLoc.IsValid()) | |
4808 return FALSE; | |
4809 m_szFirstPageObjOffset = | |
4810 pdfium::base::checked_cast<FX_FILESIZE>(safeLoc.ValueOrDie()); | |
4811 } else { | |
4812 m_szFirstPageObjOffset = | |
4813 pdfium::base::checked_cast<FX_FILESIZE>(dwFirstObjLoc); | |
4814 } | |
4815 // Item 3: The number of bits needed to represent the difference | |
4816 // between the greatest and least number of objects in a page. | |
4817 FX_DWORD dwDeltaObjectsBits = h.GetBits(16); | |
4818 // Item 4: The least length of a page in bytes. | |
4819 FX_DWORD dwPageLeastLen = h.GetBits(32); | |
4820 // Item 5: The number of bits needed to represent the difference | |
4821 // between the greatest and least length of a page, in bytes. | |
4822 FX_DWORD dwDeltaPageLenBits = h.GetBits(16); | |
4823 // Skip Item 6, 7, 8, 9 total 96 bits. | |
4824 h.SkipBits(96); | |
4825 // Item 10: The number of bits needed to represent the greatest | |
4826 // number of shared object references. | |
4827 FX_DWORD dwSharedObjBits = h.GetBits(16); | |
4828 // Item 11: The number of bits needed to represent the numerically | |
4829 // greatest shared object identifier used by the pages. | |
4830 FX_DWORD dwSharedIdBits = h.GetBits(16); | |
4831 // Item 12: The number of bits needed to represent the numerator of | |
4832 // the fractional position for each shared object reference. For each | |
4833 // shared object referenced from a page, there is an indication of | |
4834 // where in the page's content stream the object is first referenced. | |
4835 FX_DWORD dwSharedNumeratorBits = h.GetBits(16); | |
4836 // Item 13: Skip Item 13 which has 16 bits. | |
4837 FX_DWORD dwSharedDenominator = h.GetBits(16); | |
4838 CPDF_Object* pPageNum = m_pLinearizedDict->GetElementValue(FX_BSTRC("N")); | |
4839 int nPages = pPageNum ? pPageNum->GetInteger() : 0; | |
4840 if (nPages < 1) | |
4841 return FALSE; | |
4842 for (int i = 0; i < nPages; ++i) { | |
4843 FX_SAFE_DWORD safeDeltaObj = h.GetBits(dwDeltaObjectsBits); | |
4844 safeDeltaObj += dwObjLeastNum; | |
4845 if (!safeDeltaObj.IsValid()) | |
4846 return FALSE; | |
4847 m_dwDeltaNObjsArray.Add(safeDeltaObj.ValueOrDie()); | |
4848 } | |
4849 h.ByteAlign(); | |
4850 CFX_DWordArray dwPageLenArray; | |
4851 for (int i = 0; i < nPages; ++i) { | |
4852 FX_SAFE_DWORD safePageLen = h.GetBits(dwDeltaPageLenBits); | |
4853 safePageLen += dwPageLeastLen; | |
4854 if (!safePageLen.IsValid()) | |
4855 return FALSE; | |
4856 dwPageLenArray.Add(safePageLen.ValueOrDie()); | |
4857 } | |
4858 CPDF_Object* pOffsetE = m_pLinearizedDict->GetElementValue(FX_BSTRC("E")); | |
4859 int nOffsetE = pOffsetE ? pOffsetE->GetInteger() : -1; | |
4860 if (nOffsetE < 0) | |
4861 return FALSE; | |
4862 CPDF_Object* pFirstPageNum = | |
4863 m_pLinearizedDict->GetElementValue(FX_BSTRC("P")); | |
4864 int nFirstPageNum = pFirstPageNum ? pFirstPageNum->GetInteger() : 0; | |
4865 for (int i = 0; i < nPages; ++i) { | |
4866 if (i == nFirstPageNum) | |
Lei Zhang
2015/09/22 23:33:43
braces {} to match else statements
jun_fang
2015/09/23 12:26:58
Acknowledged.
I saw that your style was no braces
| |
4867 m_szPageOffsetArray.Add(m_szFirstPageObjOffset); | |
4868 else if (i == nFirstPageNum + 1) { | |
4869 if (i == 1) | |
Lei Zhang
2015/09/22 23:33:43
ditto
jun_fang
2015/09/23 12:26:58
Acknowledged.
| |
4870 m_szPageOffsetArray.Add(nOffsetE); | |
4871 else { | |
4872 m_szPageOffsetArray.Add(m_szPageOffsetArray[i - 2] + | |
4873 dwPageLenArray[i - 2]); | |
4874 } | |
4875 } else { | |
4876 if (i == 0) | |
Lei Zhang
2015/09/22 23:33:43
ditto ditto
jun_fang
2015/09/23 12:26:58
Acknowledged.
| |
4877 m_szPageOffsetArray.Add(nOffsetE); | |
4878 else { | |
4879 m_szPageOffsetArray.Add(m_szPageOffsetArray[i - 1] + | |
4880 dwPageLenArray[i - 1]); | |
4881 } | |
4882 } | |
4883 } | |
4884 if (nPages > 0) { | |
4885 m_szPageOffsetArray.Add(m_szPageOffsetArray[nPages - 1] + | |
4886 dwPageLenArray[nPages - 1]); | |
4887 } | |
4888 h.ByteAlign(); | |
4889 // number of shared objects | |
4890 for (int i = 0; i < nPages; i++) { | |
4891 m_dwNSharedObjsArray.Add(h.GetBits(dwSharedObjBits)); | |
4892 } | |
4893 h.ByteAlign(); | |
4894 // array of identifier, sizes = nshared_objects | |
4895 for (int i = 0; i < nPages; i++) { | |
4896 for (int j = 0; j < m_dwNSharedObjsArray[i]; j++) { | |
4897 m_dwIdentifierArray.Add(h.GetBits(dwSharedIdBits)); | |
4898 } | |
4899 } | |
4900 h.ByteAlign(); | |
4901 for (int i = 0; i < nPages; i++) { | |
4902 FX_SAFE_DWORD safeSize = m_dwNSharedObjsArray[i]; | |
4903 safeSize *= dwSharedNumeratorBits; | |
4904 if (!safeSize.IsValid()) | |
4905 return FALSE; | |
4906 h.SkipBits(safeSize.ValueOrDie()); | |
4907 } | |
4908 h.ByteAlign(); | |
4909 FX_SAFE_DWORD safeTotalPageLen = pdfium::base::checked_cast<FX_DWORD>(nPages); | |
4910 safeTotalPageLen *= dwDeltaPageLenBits; | |
4911 if (!safeTotalPageLen.IsValid()) | |
4912 return FALSE; | |
4913 h.SkipBits(safeTotalPageLen.ValueOrDie()); | |
4914 h.ByteAlign(); | |
4915 return TRUE; | |
4916 } | |
4917 FX_BOOL CPDF_HintTables::ReadSharedObjHintTable(CFX_BitStream& h) { | |
4918 int nStreamOffset = ReadPrimaryHintStreamOffset(h); | |
4919 int nStreamLen = ReadPrimaryHintStreamLength(h); | |
4920 if (nStreamOffset < 0 || nStreamLen < 1) | |
4921 return FALSE; | |
4922 // Item 1: The object number of the first object in the shared objects | |
4923 // section. | |
4924 FX_DWORD dwFirstSharedObjNum = h.GetBits(32); | |
4925 // Item 2: The location of the first object in the shared objects section. | |
4926 FX_DWORD dwFirstSharedObjLoc = h.GetBits(32); | |
4927 if (dwFirstSharedObjLoc > nStreamOffset) | |
4928 dwFirstSharedObjLoc += nStreamLen; | |
4929 // Item 3: The number of shared object entries for the first page. | |
4930 m_nFirstPageSharedObjs = h.GetBits(32); | |
4931 // Item 4: The number of shared object entries for the shared objects | |
4932 // section, including the number of shared object entries for the first page. | |
4933 FX_DWORD dwSharedObjTotal = h.GetBits(32); | |
4934 // Item 5: The number of bits needed to represent the greatest number of | |
4935 // objects in a shared object group. Skipped. | |
4936 h.SkipBits(16); | |
4937 // Item 6: The least length of a shared object group in bytes. | |
4938 FX_DWORD dwGroupLeastLen = h.GetBits(32); | |
4939 // Item 7: The number of bits needed to represent the difference between the | |
4940 // greatest and least length of a shared object group, in bytes. | |
4941 FX_DWORD dwDeltaGroupLen = h.GetBits(16); | |
4942 CPDF_Object* pFirstPageObj = | |
4943 m_pLinearizedDict->GetElementValue(FX_BSTRC("O")); | |
4944 int nFirstPageObjNum = pFirstPageObj ? pFirstPageObj->GetInteger() : -1; | |
4945 if (nFirstPageObjNum < 0) | |
4946 return FALSE; | |
4947 FX_DWORD dwPrevObjLen = 0; | |
4948 FX_DWORD dwCurObjLen = 0; | |
4949 for (int i = 0; i < dwSharedObjTotal; ++i) { | |
4950 dwPrevObjLen = dwCurObjLen; | |
4951 FX_SAFE_DWORD safeObjLen = h.GetBits(dwDeltaGroupLen); | |
4952 safeObjLen += dwGroupLeastLen; | |
4953 if (!safeObjLen.IsValid()) | |
4954 return FALSE; | |
4955 dwCurObjLen = safeObjLen.ValueOrDie(); | |
4956 if (i < m_nFirstPageSharedObjs) { | |
4957 m_dwSharedObjNumArray.Add(nFirstPageObjNum + i); | |
4958 if (i == 0) | |
4959 m_szSharedObjOffsetArray.Add(m_szFirstPageObjOffset); | |
4960 } else { | |
4961 FX_SAFE_DWORD safeObjNum = dwFirstSharedObjNum; | |
4962 safeObjNum += i - m_nFirstPageSharedObjs; | |
4963 if (safeObjNum.IsValid()) | |
4964 return FALSE; | |
4965 m_dwSharedObjNumArray.Add(safeObjNum.ValueOrDie()); | |
4966 if (i == m_nFirstPageSharedObjs) | |
Lei Zhang
2015/09/22 23:33:43
braces here too
| |
4967 m_szSharedObjOffsetArray.Add( | |
4968 pdfium::base::checked_cast<int32_t>(dwFirstSharedObjLoc)); | |
4969 } | |
4970 if (i != 0 && i != m_nFirstPageSharedObjs) { | |
4971 FX_SAFE_INT32 safeLoc = pdfium::base::checked_cast<int32_t>(dwPrevObjLen); | |
4972 safeLoc += m_szSharedObjOffsetArray[i - 1]; | |
4973 if (!safeLoc.IsValid()) | |
4974 return FALSE; | |
4975 m_szSharedObjOffsetArray.Add(safeLoc.ValueOrDie()); | |
4976 } | |
4977 } | |
4978 if (dwSharedObjTotal > 0) { | |
4979 FX_SAFE_INT32 safeLoc = pdfium::base::checked_cast<int32_t>(dwCurObjLen); | |
4980 safeLoc += m_szSharedObjOffsetArray[dwSharedObjTotal - 1]; | |
4981 if (!safeLoc.IsValid()) | |
4982 return FALSE; | |
4983 m_szSharedObjOffsetArray.Add(safeLoc.ValueOrDie()); | |
4984 } | |
4985 h.ByteAlign(); | |
4986 h.SkipBits(dwSharedObjTotal); | |
4987 h.ByteAlign(); | |
4988 return TRUE; | |
4989 } | |
4990 FX_BOOL CPDF_HintTables::GetPagePos(int index, | |
4991 FX_FILESIZE& szPageStartPos, | |
4992 FX_FILESIZE& szPageLength, | |
4993 FX_DWORD& dwObjNum) { | |
4994 if (!m_pLinearizedDict) | |
4995 return FALSE; | |
4996 szPageStartPos = m_szPageOffsetArray[index]; | |
4997 szPageLength = GetItemLength(index, m_szPageOffsetArray); | |
4998 CPDF_Object* pFirstPageNum = | |
4999 m_pLinearizedDict->GetElementValue(FX_BSTRC("P")); | |
5000 int nFirstPageNum = pFirstPageNum ? pFirstPageNum->GetInteger() : 0; | |
5001 CPDF_Object* pFirstPageObjNum = | |
5002 m_pLinearizedDict->GetElementValue(FX_BSTRC("O")); | |
5003 if (!pFirstPageObjNum) | |
5004 return FALSE; | |
5005 int nFirstPageObjNum = pFirstPageObjNum->GetInteger(); | |
5006 if (index == nFirstPageNum) { | |
5007 dwObjNum = nFirstPageObjNum; | |
5008 return TRUE; | |
5009 } | |
5010 // The object number of remaining pages starts from 1. | |
5011 dwObjNum = 1; | |
5012 for (int i = 0; i < index; ++i) { | |
5013 if (i == nFirstPageNum) | |
5014 continue; | |
5015 dwObjNum += m_dwDeltaNObjsArray[i]; | |
5016 } | |
5017 return TRUE; | |
5018 } | |
5019 FX_BOOL CPDF_HintTables::CheckPage(int index, IFX_DownloadHints* pHints) { | |
5020 if (!m_pLinearizedDict) | |
5021 return FALSE; | |
5022 CPDF_Object* pFirstAvailPage = | |
5023 m_pLinearizedDict->GetElementValue(FX_BSTRC("P")); | |
5024 int nFirstAvailPage = pFirstAvailPage ? pFirstAvailPage->GetInteger() : 0; | |
5025 if (index == nFirstAvailPage) | |
5026 return TRUE; | |
5027 FX_DWORD dwLength = GetItemLength(index, m_szPageOffsetArray); | |
5028 if (!dwLength || | |
5029 !m_pDataAvail->IsDataAvail(m_szPageOffsetArray[index], dwLength, | |
5030 pHints)) { | |
5031 return FALSE; | |
5032 } | |
5033 // Download data of shared objects in the page. | |
5034 FX_DWORD offset = 0; | |
5035 for (int i = 0; i < index; ++i) { | |
5036 offset += m_dwNSharedObjsArray[i]; | |
5037 } | |
5038 CPDF_Object* pFirstPageObj = | |
5039 m_pLinearizedDict->GetElementValue(FX_BSTRC("O")); | |
5040 int nFirstPageObjNum = pFirstPageObj ? pFirstPageObj->GetInteger() : -1; | |
5041 if (nFirstPageObjNum < 0) | |
5042 return FALSE; | |
5043 FX_DWORD dwIndex = 0; | |
5044 FX_DWORD dwObjNum = 0; | |
5045 for (int j = 0; j < m_dwNSharedObjsArray[index]; ++j) { | |
5046 dwIndex = m_dwIdentifierArray[offset + j]; | |
5047 dwObjNum = m_dwSharedObjNumArray[dwIndex]; | |
5048 if (dwObjNum >= nFirstPageObjNum && | |
5049 dwObjNum < nFirstPageObjNum + m_nFirstPageSharedObjs) { | |
5050 continue; | |
5051 } | |
5052 dwLength = GetItemLength(dwIndex, m_szSharedObjOffsetArray); | |
5053 if (!dwLength || | |
5054 !m_pDataAvail->IsDataAvail(m_szSharedObjOffsetArray[dwIndex], dwLength, | |
5055 pHints)) { | |
5056 return FALSE; | |
5057 } | |
5058 } | |
5059 return TRUE; | |
5060 } | |
5061 FX_BOOL CPDF_HintTables::LoadHintStream(CPDF_Stream* pHintStream) { | |
5062 if (!pHintStream || !m_pLinearizedDict) | |
5063 return FALSE; | |
5064 CPDF_Dictionary* pDict = pHintStream->GetDict(); | |
5065 CPDF_Object* pOffset = pDict ? pDict->GetElement(FX_BSTRC("S")) : nullptr; | |
5066 if (!pOffset || pOffset->GetType() != PDFOBJ_NUMBER) | |
5067 return FALSE; | |
5068 CPDF_StreamAcc acc; | |
5069 acc.LoadAllData(pHintStream); | |
5070 FX_DWORD size = acc.GetSize(); | |
5071 // The header section of page offset hint table is 36 bytes. | |
5072 // The header section of shared object hint table is 24 bytes. | |
5073 // Hint table has at least 60 bytes. | |
5074 const FX_DWORD MIN_STREAM_LEN = 60; | |
5075 if (size < MIN_STREAM_LEN || size < pOffset->GetInteger() || | |
5076 !pOffset->GetInteger()) { | |
5077 return FALSE; | |
5078 } | |
5079 CFX_BitStream bs; | |
5080 bs.Init(acc.GetData(), size); | |
5081 return ReadPageHintTable(bs) && ReadSharedObjHintTable(bs); | |
5082 } | |
5083 int CPDF_HintTables::ReadPrimaryHintStreamOffset(CFX_BitStream& hStream) const { | |
5084 if (!m_pLinearizedDict) | |
5085 return -1; | |
5086 CPDF_Array* pRange = m_pLinearizedDict->GetArray(FX_BSTRC("H")); | |
5087 if (!pRange) | |
5088 return -1; | |
5089 CPDF_Object* pStreamOffset = pRange->GetElementValue(0); | |
5090 if (!pStreamOffset) | |
5091 return -1; | |
5092 return pStreamOffset->GetInteger(); | |
5093 } | |
5094 int CPDF_HintTables::ReadPrimaryHintStreamLength(CFX_BitStream& hStream) const { | |
5095 if (!m_pLinearizedDict) | |
5096 return -1; | |
5097 CPDF_Array* pRange = m_pLinearizedDict->GetArray(FX_BSTRC("H")); | |
5098 if (!pRange) | |
5099 return -1; | |
5100 CPDF_Object* pStreamLen = pRange->GetElementValue(1); | |
5101 if (!pStreamLen) | |
5102 return -1; | |
5103 return pStreamLen->GetInteger(); | |
5104 } | |
OLD | NEW |