Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(602)

Side by Side Diff: core/fpdfapi/fpdf_parser/cpdf_parser.cpp

Issue 1910063004: Add a simple check for V4 cross reference table (Closed) Base URL: https://pdfium.googlesource.com/pdfium.git@master
Patch Set: address comments Created 4 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « DEPS ('k') | core/fpdfapi/fpdf_parser/cpdf_parser_embeddertest.cpp » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2016 PDFium Authors. All rights reserved. 1 // Copyright 2016 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 "core/fpdfapi/fpdf_parser/include/cpdf_parser.h" 7 #include "core/fpdfapi/fpdf_parser/include/cpdf_parser.h"
8 8
9 #include <vector> 9 #include <vector>
10 10
(...skipping 298 matching lines...) Expand 10 before | Expand all | Expand 10 after
309 if (GetObjectType(objnum) == 1) 309 if (GetObjectType(objnum) == 1)
310 return GetObjectPositionOrZero(objnum); 310 return GetObjectPositionOrZero(objnum);
311 311
312 if (GetObjectType(objnum) == 2) { 312 if (GetObjectType(objnum) == 2) {
313 FX_FILESIZE pos = GetObjectPositionOrZero(objnum); 313 FX_FILESIZE pos = GetObjectPositionOrZero(objnum);
314 return GetObjectPositionOrZero(pos); 314 return GetObjectPositionOrZero(pos);
315 } 315 }
316 return 0; 316 return 0;
317 } 317 }
318 318
319 // Ideally, all the cross reference entries should be verified.
320 // In reality, we rarely see well-formed cross references don't match
321 // with the objects. crbug/602650 showed a case where object numbers
322 // in the cross reference table are all off by one.
323 bool CPDF_Parser::VerifyCrossRefV4() {
324 for (const auto& it : m_ObjectInfo) {
325 if (it.second.pos == 0)
326 continue;
327 // Find the first non-zero position.
328 FX_FILESIZE SavedPos = m_pSyntax->SavePos();
329 m_pSyntax->RestorePos(it.second.pos);
330 bool is_num = false;
331 CFX_ByteString num_str = m_pSyntax->GetNextWord(&is_num);
332 m_pSyntax->RestorePos(SavedPos);
333 if (!is_num || num_str.IsEmpty() ||
334 FXSYS_atoui(num_str.c_str()) != it.first) {
335 // If the object number read doesn't match the one stored,
336 // something is wrong with the cross reference table.
337 return false;
338 } else {
339 return true;
340 }
341 }
342 return true;
343 }
344
319 FX_BOOL CPDF_Parser::LoadAllCrossRefV4(FX_FILESIZE xrefpos) { 345 FX_BOOL CPDF_Parser::LoadAllCrossRefV4(FX_FILESIZE xrefpos) {
320 if (!LoadCrossRefV4(xrefpos, 0, TRUE)) 346 if (!LoadCrossRefV4(xrefpos, 0, TRUE))
321 return FALSE; 347 return FALSE;
322 348
323 m_pTrailer = LoadTrailerV4(); 349 m_pTrailer = LoadTrailerV4();
324 if (!m_pTrailer) 350 if (!m_pTrailer)
325 return FALSE; 351 return FALSE;
326 352
327 int32_t xrefsize = GetDirectInteger(m_pTrailer, "Size"); 353 int32_t xrefsize = GetDirectInteger(m_pTrailer, "Size");
328 if (xrefsize > 0 && xrefsize <= kMaxXRefSize) 354 if (xrefsize > 0 && xrefsize <= kMaxXRefSize)
(...skipping 30 matching lines...) Expand all
359 385
360 // SLOW ... 386 // SLOW ...
361 XRefStreamList.insert(XRefStreamList.begin(), 387 XRefStreamList.insert(XRefStreamList.begin(),
362 pDict->GetIntegerBy("XRefStm")); 388 pDict->GetIntegerBy("XRefStm"));
363 m_Trailers.Add(pDict.release()); 389 m_Trailers.Add(pDict.release());
364 } 390 }
365 391
366 for (size_t i = 0; i < CrossRefList.size(); ++i) { 392 for (size_t i = 0; i < CrossRefList.size(); ++i) {
367 if (!LoadCrossRefV4(CrossRefList[i], XRefStreamList[i], FALSE)) 393 if (!LoadCrossRefV4(CrossRefList[i], XRefStreamList[i], FALSE))
368 return FALSE; 394 return FALSE;
395 if (i == 0 && !VerifyCrossRefV4())
396 return FALSE;
369 } 397 }
370 return TRUE; 398 return TRUE;
371 } 399 }
372 400
373 FX_BOOL CPDF_Parser::LoadLinearizedAllCrossRefV4(FX_FILESIZE xrefpos, 401 FX_BOOL CPDF_Parser::LoadLinearizedAllCrossRefV4(FX_FILESIZE xrefpos,
374 uint32_t dwObjCount) { 402 uint32_t dwObjCount) {
375 if (!LoadLinearizedCrossRefV4(xrefpos, dwObjCount)) 403 if (!LoadLinearizedCrossRefV4(xrefpos, dwObjCount))
376 return FALSE; 404 return FALSE;
377 405
378 m_pTrailer = LoadTrailerV4(); 406 m_pTrailer = LoadTrailerV4();
(...skipping 1263 matching lines...) Expand 10 before | Expand all | Expand 10 after
1642 if (!LoadLinearizedAllCrossRefV4(m_LastXRefOffset, m_dwXrefStartObjNum) && 1670 if (!LoadLinearizedAllCrossRefV4(m_LastXRefOffset, m_dwXrefStartObjNum) &&
1643 !LoadLinearizedAllCrossRefV5(m_LastXRefOffset)) { 1671 !LoadLinearizedAllCrossRefV5(m_LastXRefOffset)) {
1644 m_LastXRefOffset = 0; 1672 m_LastXRefOffset = 0;
1645 m_pSyntax->m_MetadataObjnum = dwSaveMetadataObjnum; 1673 m_pSyntax->m_MetadataObjnum = dwSaveMetadataObjnum;
1646 return FORMAT_ERROR; 1674 return FORMAT_ERROR;
1647 } 1675 }
1648 1676
1649 m_pSyntax->m_MetadataObjnum = dwSaveMetadataObjnum; 1677 m_pSyntax->m_MetadataObjnum = dwSaveMetadataObjnum;
1650 return SUCCESS; 1678 return SUCCESS;
1651 } 1679 }
OLDNEW
« no previous file with comments | « DEPS ('k') | core/fpdfapi/fpdf_parser/cpdf_parser_embeddertest.cpp » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698