OLD | NEW |
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/parser/cpdf_data_avail.h" | 7 #include "core/fpdfapi/parser/cpdf_data_avail.h" |
8 | 8 |
9 #include <algorithm> | 9 #include <algorithm> |
10 #include <memory> | 10 #include <memory> |
11 #include <utility> | 11 #include <utility> |
12 | 12 |
13 #include "core/fpdfapi/cpdf_modulemgr.h" | 13 #include "core/fpdfapi/cpdf_modulemgr.h" |
14 #include "core/fpdfapi/parser/cpdf_array.h" | 14 #include "core/fpdfapi/parser/cpdf_array.h" |
15 #include "core/fpdfapi/parser/cpdf_dictionary.h" | 15 #include "core/fpdfapi/parser/cpdf_dictionary.h" |
16 #include "core/fpdfapi/parser/cpdf_document.h" | 16 #include "core/fpdfapi/parser/cpdf_document.h" |
17 #include "core/fpdfapi/parser/cpdf_hint_tables.h" | 17 #include "core/fpdfapi/parser/cpdf_hint_tables.h" |
18 #include "core/fpdfapi/parser/cpdf_linearized_header.h" | 18 #include "core/fpdfapi/parser/cpdf_linearized_header.h" |
19 #include "core/fpdfapi/parser/cpdf_name.h" | 19 #include "core/fpdfapi/parser/cpdf_name.h" |
20 #include "core/fpdfapi/parser/cpdf_number.h" | 20 #include "core/fpdfapi/parser/cpdf_number.h" |
21 #include "core/fpdfapi/parser/cpdf_reference.h" | 21 #include "core/fpdfapi/parser/cpdf_reference.h" |
22 #include "core/fpdfapi/parser/cpdf_stream.h" | 22 #include "core/fpdfapi/parser/cpdf_stream.h" |
23 #include "core/fpdfapi/parser/fpdf_parser_utility.h" | 23 #include "core/fpdfapi/parser/fpdf_parser_utility.h" |
24 #include "core/fxcrt/fx_ext.h" | 24 #include "core/fxcrt/fx_ext.h" |
25 #include "core/fxcrt/fx_safe_types.h" | 25 #include "core/fxcrt/fx_safe_types.h" |
| 26 #include "third_party/base/numerics/safe_conversions.h" |
26 #include "third_party/base/stl_util.h" | 27 #include "third_party/base/stl_util.h" |
27 | 28 |
28 CPDF_DataAvail::FileAvail::~FileAvail() {} | 29 CPDF_DataAvail::FileAvail::~FileAvail() {} |
29 | 30 |
30 CPDF_DataAvail::DownloadHints::~DownloadHints() {} | 31 CPDF_DataAvail::DownloadHints::~DownloadHints() {} |
31 | 32 |
32 // static | 33 // static |
33 int CPDF_DataAvail::s_CurrentDataAvailRecursionDepth = 0; | 34 int CPDF_DataAvail::s_CurrentDataAvailRecursionDepth = 0; |
34 | 35 |
35 CPDF_DataAvail::CPDF_DataAvail(FileAvail* pFileAvail, | 36 CPDF_DataAvail::CPDF_DataAvail(FileAvail* pFileAvail, |
(...skipping 22 matching lines...) Expand all Loading... |
58 m_bDocAvail = false; | 59 m_bDocAvail = false; |
59 m_bPagesLoad = false; | 60 m_bPagesLoad = false; |
60 m_bPagesTreeLoad = false; | 61 m_bPagesTreeLoad = false; |
61 m_bMainXRefLoadedOK = false; | 62 m_bMainXRefLoadedOK = false; |
62 m_bAnnotsLoad = false; | 63 m_bAnnotsLoad = false; |
63 m_bHaveAcroForm = false; | 64 m_bHaveAcroForm = false; |
64 m_bAcroFormLoad = false; | 65 m_bAcroFormLoad = false; |
65 m_bPageLoadedOK = false; | 66 m_bPageLoadedOK = false; |
66 m_bNeedDownLoadResource = false; | 67 m_bNeedDownLoadResource = false; |
67 m_bLinearizedFormParamLoad = false; | 68 m_bLinearizedFormParamLoad = false; |
68 m_pRoot = nullptr; | |
69 m_pTrailer = nullptr; | 69 m_pTrailer = nullptr; |
70 m_pCurrentParser = nullptr; | 70 m_pCurrentParser = nullptr; |
71 m_pAcroForm = nullptr; | 71 m_pAcroForm = nullptr; |
72 m_pPageDict = nullptr; | 72 m_pPageDict = nullptr; |
73 m_pPageResource = nullptr; | 73 m_pPageResource = nullptr; |
74 m_docStatus = PDF_DATAAVAIL_HEADER; | 74 m_docStatus = PDF_DATAAVAIL_HEADER; |
75 m_parser.m_bOwnFileRead = false; | 75 m_parser.m_bOwnFileRead = false; |
76 m_bTotalLoadPageTree = false; | 76 m_bTotalLoadPageTree = false; |
77 m_bCurPageDictLoadOK = false; | 77 m_bCurPageDictLoadOK = false; |
78 m_bLinearedDataOK = false; | 78 m_bLinearedDataOK = false; |
79 m_bSupportHintTable = bSupportHintTable; | 79 m_bSupportHintTable = bSupportHintTable; |
80 } | 80 } |
81 | 81 |
82 CPDF_DataAvail::~CPDF_DataAvail() { | 82 CPDF_DataAvail::~CPDF_DataAvail() { |
83 m_pHintTables.reset(); | 83 m_pHintTables.reset(); |
84 | |
85 for (CPDF_Object* pObject : m_arrayAcroforms) | 84 for (CPDF_Object* pObject : m_arrayAcroforms) |
86 delete pObject; | 85 delete pObject; |
87 } | 86 } |
88 | 87 |
89 void CPDF_DataAvail::SetDocument(CPDF_Document* pDoc) { | 88 void CPDF_DataAvail::SetDocument(CPDF_Document* pDoc) { |
90 m_pDocument = pDoc; | 89 m_pDocument = pDoc; |
91 } | 90 } |
92 | 91 |
93 uint32_t CPDF_DataAvail::GetObjectSize(uint32_t objnum, FX_FILESIZE& offset) { | 92 uint32_t CPDF_DataAvail::GetObjectSize(uint32_t objnum, FX_FILESIZE& offset) { |
94 CPDF_Parser* pParser = m_pDocument->GetParser(); | 93 CPDF_Parser* pParser = m_pDocument->GetParser(); |
(...skipping 126 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
221 | 220 |
222 for (CPDF_Object* pObject : m_arrayAcroforms) | 221 for (CPDF_Object* pObject : m_arrayAcroforms) |
223 delete pObject; | 222 delete pObject; |
224 | 223 |
225 m_arrayAcroforms.clear(); | 224 m_arrayAcroforms.clear(); |
226 return true; | 225 return true; |
227 } | 226 } |
228 | 227 |
229 bool CPDF_DataAvail::CheckAcroForm(DownloadHints* pHints) { | 228 bool CPDF_DataAvail::CheckAcroForm(DownloadHints* pHints) { |
230 bool bExist = false; | 229 bool bExist = false; |
231 m_pAcroForm = GetObject(m_dwAcroFormObjNum, pHints, &bExist); | 230 m_pAcroForm = GetObject(m_dwAcroFormObjNum, pHints, &bExist).release(); |
232 if (!bExist) { | 231 if (!bExist) { |
233 m_docStatus = PDF_DATAAVAIL_PAGETREE; | 232 m_docStatus = PDF_DATAAVAIL_PAGETREE; |
234 return true; | 233 return true; |
235 } | 234 } |
236 | 235 |
237 if (!m_pAcroForm) { | 236 if (!m_pAcroForm) { |
238 if (m_docStatus == PDF_DATAAVAIL_ERROR) { | 237 if (m_docStatus == PDF_DATAAVAIL_ERROR) { |
239 m_docStatus = PDF_DATAAVAIL_LOADALLFILE; | 238 m_docStatus = PDF_DATAAVAIL_LOADALLFILE; |
240 return true; | 239 return true; |
241 } | 240 } |
(...skipping 89 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
331 return false; | 330 return false; |
332 } | 331 } |
333 | 332 |
334 m_dwRootObjNum = m_parser.GetRootObjNum(); | 333 m_dwRootObjNum = m_parser.GetRootObjNum(); |
335 m_dwInfoObjNum = m_parser.GetInfoObjNum(); | 334 m_dwInfoObjNum = m_parser.GetInfoObjNum(); |
336 m_pCurrentParser = &m_parser; | 335 m_pCurrentParser = &m_parser; |
337 m_docStatus = PDF_DATAAVAIL_ROOT; | 336 m_docStatus = PDF_DATAAVAIL_ROOT; |
338 return true; | 337 return true; |
339 } | 338 } |
340 | 339 |
341 CPDF_Object* CPDF_DataAvail::GetObject(uint32_t objnum, | 340 std::unique_ptr<CPDF_Object> CPDF_DataAvail::GetObject(uint32_t objnum, |
342 DownloadHints* pHints, | 341 DownloadHints* pHints, |
343 bool* pExistInFile) { | 342 bool* pExistInFile) { |
344 CPDF_Object* pRet = nullptr; | |
345 uint32_t size = 0; | 343 uint32_t size = 0; |
346 FX_FILESIZE offset = 0; | 344 FX_FILESIZE offset = 0; |
347 CPDF_Parser* pParser = nullptr; | 345 CPDF_Parser* pParser = nullptr; |
348 | 346 |
349 if (pExistInFile) | 347 if (pExistInFile) |
350 *pExistInFile = true; | 348 *pExistInFile = true; |
351 | 349 |
352 if (m_pDocument) { | 350 if (m_pDocument) { |
353 size = GetObjectSize(objnum, offset); | 351 size = GetObjectSize(objnum, offset); |
354 pParser = m_pDocument->GetParser(); | 352 pParser = m_pDocument->GetParser(); |
355 } else { | 353 } else { |
356 size = (uint32_t)m_parser.GetObjectSize(objnum); | 354 size = (uint32_t)m_parser.GetObjectSize(objnum); |
357 offset = m_parser.GetObjectOffset(objnum); | 355 offset = m_parser.GetObjectOffset(objnum); |
358 pParser = &m_parser; | 356 pParser = &m_parser; |
359 } | 357 } |
360 | 358 |
361 if (!IsDataAvail(offset, size, pHints)) | 359 if (!IsDataAvail(offset, size, pHints)) |
362 return nullptr; | 360 return nullptr; |
363 | 361 |
| 362 std::unique_ptr<CPDF_Object> pRet; |
364 if (pParser) | 363 if (pParser) |
365 pRet = pParser->ParseIndirectObject(nullptr, objnum); | 364 pRet = pParser->ParseIndirectObject(nullptr, objnum); |
366 | 365 |
367 if (!pRet && pExistInFile) | 366 if (!pRet && pExistInFile) |
368 *pExistInFile = false; | 367 *pExistInFile = false; |
369 | 368 |
370 return pRet; | 369 return pRet; |
371 } | 370 } |
372 | 371 |
373 bool CPDF_DataAvail::CheckInfo(DownloadHints* pHints) { | 372 bool CPDF_DataAvail::CheckInfo(DownloadHints* pHints) { |
374 bool bExist = false; | 373 bool bExist = false; |
375 CPDF_Object* pInfo = GetObject(m_dwInfoObjNum, pHints, &bExist); | 374 std::unique_ptr<CPDF_Object> pInfo = |
376 if (!bExist) { | 375 GetObject(m_dwInfoObjNum, pHints, &bExist); |
377 m_docStatus = | 376 if (bExist && !pInfo) { |
378 (m_bHaveAcroForm ? PDF_DATAAVAIL_ACROFORM : PDF_DATAAVAIL_PAGETREE); | |
379 return true; | |
380 } | |
381 | |
382 if (!pInfo) { | |
383 if (m_docStatus == PDF_DATAAVAIL_ERROR) { | 377 if (m_docStatus == PDF_DATAAVAIL_ERROR) { |
384 m_docStatus = PDF_DATAAVAIL_LOADALLFILE; | 378 m_docStatus = PDF_DATAAVAIL_LOADALLFILE; |
385 return true; | 379 return true; |
386 } | 380 } |
387 | |
388 if (m_Pos == m_dwFileLen) | 381 if (m_Pos == m_dwFileLen) |
389 m_docStatus = PDF_DATAAVAIL_ERROR; | 382 m_docStatus = PDF_DATAAVAIL_ERROR; |
390 return false; | 383 return false; |
391 } | 384 } |
392 | |
393 delete pInfo; | |
394 m_docStatus = | 385 m_docStatus = |
395 (m_bHaveAcroForm ? PDF_DATAAVAIL_ACROFORM : PDF_DATAAVAIL_PAGETREE); | 386 m_bHaveAcroForm ? PDF_DATAAVAIL_ACROFORM : PDF_DATAAVAIL_PAGETREE; |
396 | |
397 return true; | 387 return true; |
398 } | 388 } |
399 | 389 |
400 bool CPDF_DataAvail::CheckRoot(DownloadHints* pHints) { | 390 bool CPDF_DataAvail::CheckRoot(DownloadHints* pHints) { |
401 bool bExist = false; | 391 bool bExist = false; |
402 m_pRoot = GetObject(m_dwRootObjNum, pHints, &bExist); | 392 m_pRoot = GetObject(m_dwRootObjNum, pHints, &bExist); |
403 if (!bExist) { | 393 if (!bExist) { |
404 m_docStatus = PDF_DATAAVAIL_LOADALLFILE; | 394 m_docStatus = PDF_DATAAVAIL_LOADALLFILE; |
405 return true; | 395 return true; |
406 } | 396 } |
(...skipping 57 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
464 void CPDF_DataAvail::ResetFirstCheck(uint32_t dwPage) { | 454 void CPDF_DataAvail::ResetFirstCheck(uint32_t dwPage) { |
465 m_pageMapCheckState.erase(dwPage); | 455 m_pageMapCheckState.erase(dwPage); |
466 } | 456 } |
467 | 457 |
468 bool CPDF_DataAvail::CheckPage(DownloadHints* pHints) { | 458 bool CPDF_DataAvail::CheckPage(DownloadHints* pHints) { |
469 uint32_t iPageObjs = m_PageObjList.GetSize(); | 459 uint32_t iPageObjs = m_PageObjList.GetSize(); |
470 CFX_ArrayTemplate<uint32_t> UnavailObjList; | 460 CFX_ArrayTemplate<uint32_t> UnavailObjList; |
471 for (uint32_t i = 0; i < iPageObjs; ++i) { | 461 for (uint32_t i = 0; i < iPageObjs; ++i) { |
472 uint32_t dwPageObjNum = m_PageObjList.GetAt(i); | 462 uint32_t dwPageObjNum = m_PageObjList.GetAt(i); |
473 bool bExist = false; | 463 bool bExist = false; |
474 CPDF_Object* pObj = GetObject(dwPageObjNum, pHints, &bExist); | 464 std::unique_ptr<CPDF_Object> pObj = |
| 465 GetObject(dwPageObjNum, pHints, &bExist); |
475 if (!pObj) { | 466 if (!pObj) { |
476 if (bExist) | 467 if (bExist) |
477 UnavailObjList.Add(dwPageObjNum); | 468 UnavailObjList.Add(dwPageObjNum); |
478 continue; | 469 continue; |
479 } | 470 } |
480 | 471 |
481 CPDF_Array* pArray = ToArray(pObj); | 472 CPDF_Array* pArray = ToArray(pObj.get()); |
482 if (pArray) { | 473 if (pArray) { |
483 for (CPDF_Object* pArrayObj : *pArray) { | 474 for (CPDF_Object* pArrayObj : *pArray) { |
484 if (CPDF_Reference* pRef = ToReference(pArrayObj)) | 475 if (CPDF_Reference* pRef = ToReference(pArrayObj)) |
485 UnavailObjList.Add(pRef->GetRefObjNum()); | 476 UnavailObjList.Add(pRef->GetRefObjNum()); |
486 } | 477 } |
487 } | 478 } |
488 | 479 |
489 if (!pObj->IsDictionary()) { | 480 if (!pObj->IsDictionary()) { |
490 delete pObj; | |
491 continue; | 481 continue; |
492 } | 482 } |
493 | 483 |
494 CFX_ByteString type = pObj->GetDict()->GetStringFor("Type"); | 484 CFX_ByteString type = pObj->GetDict()->GetStringFor("Type"); |
495 if (type == "Pages") { | 485 if (type == "Pages") { |
496 m_PagesArray.push_back(pObj); | 486 m_PagesArray.push_back(std::move(pObj)); |
497 continue; | 487 continue; |
498 } | 488 } |
499 delete pObj; | |
500 } | 489 } |
501 | 490 |
502 m_PageObjList.RemoveAll(); | 491 m_PageObjList.RemoveAll(); |
503 if (UnavailObjList.GetSize()) { | 492 if (UnavailObjList.GetSize()) { |
504 m_PageObjList.Append(UnavailObjList); | 493 m_PageObjList.Append(UnavailObjList); |
505 return false; | 494 return false; |
506 } | 495 } |
507 | 496 |
508 uint32_t iPages = m_PagesArray.size(); | 497 uint32_t iPages = m_PagesArray.size(); |
509 for (uint32_t i = 0; i < iPages; i++) { | 498 for (uint32_t i = 0; i < iPages; i++) { |
510 CPDF_Object* pPages = m_PagesArray[i]; | 499 std::unique_ptr<CPDF_Object> pPages = std::move(m_PagesArray[i]); |
511 if (!pPages) | 500 if (pPages && !GetPageKids(m_pCurrentParser, pPages.get())) { |
512 continue; | |
513 | |
514 if (!GetPageKids(m_pCurrentParser, pPages)) { | |
515 delete pPages; | |
516 while (++i < iPages) | |
517 delete m_PagesArray[i]; | |
518 | |
519 m_PagesArray.clear(); | 501 m_PagesArray.clear(); |
520 m_docStatus = PDF_DATAAVAIL_ERROR; | 502 m_docStatus = PDF_DATAAVAIL_ERROR; |
521 return false; | 503 return false; |
522 } | 504 } |
523 delete pPages; | |
524 } | 505 } |
525 | |
526 m_PagesArray.clear(); | 506 m_PagesArray.clear(); |
527 if (!m_PageObjList.GetSize()) | 507 if (!m_PageObjList.GetSize()) |
528 m_docStatus = PDF_DATAAVAIL_DONE; | 508 m_docStatus = PDF_DATAAVAIL_DONE; |
| 509 |
529 return true; | 510 return true; |
530 } | 511 } |
531 | 512 |
532 bool CPDF_DataAvail::GetPageKids(CPDF_Parser* pParser, CPDF_Object* pPages) { | 513 bool CPDF_DataAvail::GetPageKids(CPDF_Parser* pParser, CPDF_Object* pPages) { |
533 if (!pParser) { | 514 if (!pParser) { |
534 m_docStatus = PDF_DATAAVAIL_ERROR; | 515 m_docStatus = PDF_DATAAVAIL_ERROR; |
535 return false; | 516 return false; |
536 } | 517 } |
537 | 518 |
538 CPDF_Dictionary* pDict = pPages->GetDict(); | 519 CPDF_Dictionary* pDict = pPages->GetDict(); |
(...skipping 14 matching lines...) Expand all Loading... |
553 } break; | 534 } break; |
554 default: | 535 default: |
555 m_docStatus = PDF_DATAAVAIL_ERROR; | 536 m_docStatus = PDF_DATAAVAIL_ERROR; |
556 return false; | 537 return false; |
557 } | 538 } |
558 return true; | 539 return true; |
559 } | 540 } |
560 | 541 |
561 bool CPDF_DataAvail::CheckPages(DownloadHints* pHints) { | 542 bool CPDF_DataAvail::CheckPages(DownloadHints* pHints) { |
562 bool bExist = false; | 543 bool bExist = false; |
563 CPDF_Object* pPages = GetObject(m_PagesObjNum, pHints, &bExist); | 544 std::unique_ptr<CPDF_Object> pPages = |
| 545 GetObject(m_PagesObjNum, pHints, &bExist); |
564 if (!bExist) { | 546 if (!bExist) { |
565 m_docStatus = PDF_DATAAVAIL_LOADALLFILE; | 547 m_docStatus = PDF_DATAAVAIL_LOADALLFILE; |
566 return true; | 548 return true; |
567 } | 549 } |
568 | 550 |
569 if (!pPages) { | 551 if (!pPages) { |
570 if (m_docStatus == PDF_DATAAVAIL_ERROR) { | 552 if (m_docStatus == PDF_DATAAVAIL_ERROR) { |
571 m_docStatus = PDF_DATAAVAIL_LOADALLFILE; | 553 m_docStatus = PDF_DATAAVAIL_LOADALLFILE; |
572 return true; | 554 return true; |
573 } | 555 } |
574 return false; | 556 return false; |
575 } | 557 } |
576 | 558 |
577 if (!GetPageKids(m_pCurrentParser, pPages)) { | 559 if (!GetPageKids(m_pCurrentParser, pPages.get())) { |
578 delete pPages; | |
579 m_docStatus = PDF_DATAAVAIL_ERROR; | 560 m_docStatus = PDF_DATAAVAIL_ERROR; |
580 return false; | 561 return false; |
581 } | 562 } |
582 | 563 |
583 delete pPages; | |
584 m_docStatus = PDF_DATAAVAIL_PAGE; | 564 m_docStatus = PDF_DATAAVAIL_PAGE; |
585 return true; | 565 return true; |
586 } | 566 } |
587 | 567 |
588 bool CPDF_DataAvail::CheckHeader(DownloadHints* pHints) { | 568 bool CPDF_DataAvail::CheckHeader(DownloadHints* pHints) { |
589 ASSERT(m_dwFileLen >= 0); | 569 ASSERT(m_dwFileLen >= 0); |
590 const uint32_t kReqSize = std::min(static_cast<uint32_t>(m_dwFileLen), 1024U); | 570 const uint32_t kReqSize = std::min(static_cast<uint32_t>(m_dwFileLen), 1024U); |
591 | 571 |
592 if (m_pFileAvail->IsDataAvail(0, kReqSize)) { | 572 if (m_pFileAvail->IsDataAvail(0, kReqSize)) { |
593 uint8_t buffer[1024]; | 573 uint8_t buffer[1024]; |
(...skipping 104 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
698 std::unique_ptr<CPDF_Object> pHintStream( | 678 std::unique_ptr<CPDF_Object> pHintStream( |
699 ParseIndirectObjectAt(szHintStart, 0)); | 679 ParseIndirectObjectAt(szHintStart, 0)); |
700 CPDF_Stream* pStream = ToStream(pHintStream.get()); | 680 CPDF_Stream* pStream = ToStream(pHintStream.get()); |
701 if (pStream && pHintTables->LoadHintStream(pStream)) | 681 if (pStream && pHintTables->LoadHintStream(pStream)) |
702 m_pHintTables = std::move(pHintTables); | 682 m_pHintTables = std::move(pHintTables); |
703 | 683 |
704 m_docStatus = PDF_DATAAVAIL_DONE; | 684 m_docStatus = PDF_DATAAVAIL_DONE; |
705 return true; | 685 return true; |
706 } | 686 } |
707 | 687 |
708 CPDF_Object* CPDF_DataAvail::ParseIndirectObjectAt( | 688 std::unique_ptr<CPDF_Object> CPDF_DataAvail::ParseIndirectObjectAt( |
709 FX_FILESIZE pos, | 689 FX_FILESIZE pos, |
710 uint32_t objnum, | 690 uint32_t objnum, |
711 CPDF_IndirectObjectHolder* pObjList) { | 691 CPDF_IndirectObjectHolder* pObjList) { |
712 FX_FILESIZE SavedPos = m_syntaxParser.SavePos(); | 692 FX_FILESIZE SavedPos = m_syntaxParser.SavePos(); |
713 m_syntaxParser.RestorePos(pos); | 693 m_syntaxParser.RestorePos(pos); |
714 | 694 |
715 bool bIsNumber; | 695 bool bIsNumber; |
716 CFX_ByteString word = m_syntaxParser.GetNextWord(&bIsNumber); | 696 CFX_ByteString word = m_syntaxParser.GetNextWord(&bIsNumber); |
717 if (!bIsNumber) | 697 if (!bIsNumber) |
718 return nullptr; | 698 return nullptr; |
719 | 699 |
720 uint32_t parser_objnum = FXSYS_atoui(word.c_str()); | 700 uint32_t parser_objnum = FXSYS_atoui(word.c_str()); |
721 if (objnum && parser_objnum != objnum) | 701 if (objnum && parser_objnum != objnum) |
722 return nullptr; | 702 return nullptr; |
723 | 703 |
724 word = m_syntaxParser.GetNextWord(&bIsNumber); | 704 word = m_syntaxParser.GetNextWord(&bIsNumber); |
725 if (!bIsNumber) | 705 if (!bIsNumber) |
726 return nullptr; | 706 return nullptr; |
727 | 707 |
728 uint32_t gennum = FXSYS_atoui(word.c_str()); | 708 uint32_t gennum = FXSYS_atoui(word.c_str()); |
729 if (m_syntaxParser.GetKeyword() != "obj") { | 709 if (m_syntaxParser.GetKeyword() != "obj") { |
730 m_syntaxParser.RestorePos(SavedPos); | 710 m_syntaxParser.RestorePos(SavedPos); |
731 return nullptr; | 711 return nullptr; |
732 } | 712 } |
733 | 713 |
734 CPDF_Object* pObj = | 714 std::unique_ptr<CPDF_Object> pObj = |
735 m_syntaxParser.GetObject(pObjList, parser_objnum, gennum, true); | 715 m_syntaxParser.GetObject(pObjList, parser_objnum, gennum, true); |
736 m_syntaxParser.RestorePos(SavedPos); | 716 m_syntaxParser.RestorePos(SavedPos); |
737 return pObj; | 717 return pObj; |
738 } | 718 } |
739 | 719 |
740 CPDF_DataAvail::DocLinearizationStatus CPDF_DataAvail::IsLinearizedPDF() { | 720 CPDF_DataAvail::DocLinearizationStatus CPDF_DataAvail::IsLinearizedPDF() { |
741 const uint32_t kReqSize = 1024; | 721 const uint32_t kReqSize = 1024; |
742 if (!m_pFileAvail->IsDataAvail(0, kReqSize)) | 722 if (!m_pFileAvail->IsDataAvail(0, kReqSize)) |
743 return LinearizationUnknown; | 723 return LinearizationUnknown; |
744 | 724 |
(...skipping 14 matching lines...) Expand all Loading... |
759 | 739 |
760 bool CPDF_DataAvail::IsLinearized() { | 740 bool CPDF_DataAvail::IsLinearized() { |
761 return !!m_pLinearized; | 741 return !!m_pLinearized; |
762 } | 742 } |
763 | 743 |
764 bool CPDF_DataAvail::IsLinearizedFile(uint8_t* pData, uint32_t dwLen) { | 744 bool CPDF_DataAvail::IsLinearizedFile(uint8_t* pData, uint32_t dwLen) { |
765 if (m_pLinearized) | 745 if (m_pLinearized) |
766 return true; | 746 return true; |
767 | 747 |
768 ScopedFileStream file(FX_CreateMemoryStream(pData, (size_t)dwLen, false)); | 748 ScopedFileStream file(FX_CreateMemoryStream(pData, (size_t)dwLen, false)); |
769 | |
770 int32_t offset = GetHeaderOffset(file.get()); | 749 int32_t offset = GetHeaderOffset(file.get()); |
771 if (offset == -1) { | 750 if (offset == -1) { |
772 m_docStatus = PDF_DATAAVAIL_ERROR; | 751 m_docStatus = PDF_DATAAVAIL_ERROR; |
773 return false; | 752 return false; |
774 } | 753 } |
775 | 754 |
776 m_dwHeaderOffset = offset; | 755 m_dwHeaderOffset = offset; |
777 m_syntaxParser.InitParser(file.get(), offset); | 756 m_syntaxParser.InitParser(file.get(), offset); |
778 m_syntaxParser.RestorePos(m_syntaxParser.m_HeaderOffset + 9); | 757 m_syntaxParser.RestorePos(m_syntaxParser.m_HeaderOffset + 9); |
779 | 758 |
780 bool bNumber; | 759 bool bNumber; |
781 CFX_ByteString wordObjNum = m_syntaxParser.GetNextWord(&bNumber); | 760 CFX_ByteString wordObjNum = m_syntaxParser.GetNextWord(&bNumber); |
782 if (!bNumber) | 761 if (!bNumber) |
783 return false; | 762 return false; |
784 | 763 |
785 uint32_t objnum = FXSYS_atoui(wordObjNum.c_str()); | 764 uint32_t objnum = FXSYS_atoui(wordObjNum.c_str()); |
786 m_pLinearized = CPDF_LinearizedHeader::CreateForObject(pdfium::WrapUnique( | 765 m_pLinearized = CPDF_LinearizedHeader::CreateForObject( |
787 ParseIndirectObjectAt(m_syntaxParser.m_HeaderOffset + 9, objnum))); | 766 ParseIndirectObjectAt(m_syntaxParser.m_HeaderOffset + 9, objnum)); |
788 if (!m_pLinearized || | 767 if (!m_pLinearized || |
789 m_pLinearized->GetFileSize() != m_pFileRead->GetSize()) { | 768 m_pLinearized->GetFileSize() != m_pFileRead->GetSize()) { |
790 m_pLinearized.reset(); | 769 m_pLinearized.reset(); |
791 return false; | 770 return false; |
792 } | 771 } |
793 return true; | 772 return true; |
794 } | 773 } |
795 | 774 |
796 bool CPDF_DataAvail::CheckEnd(DownloadHints* pHints) { | 775 bool CPDF_DataAvail::CheckEnd(DownloadHints* pHints) { |
797 uint32_t req_pos = (uint32_t)(m_dwFileLen > 1024 ? m_dwFileLen - 1024 : 0); | 776 uint32_t req_pos = (uint32_t)(m_dwFileLen > 1024 ? m_dwFileLen - 1024 : 0); |
(...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
850 | 829 |
851 ScopedFileStream file(FX_CreateMemoryStream(pBuf, (size_t)iSize, false)); | 830 ScopedFileStream file(FX_CreateMemoryStream(pBuf, (size_t)iSize, false)); |
852 m_parser.m_pSyntax->InitParser(file.get(), 0); | 831 m_parser.m_pSyntax->InitParser(file.get(), 0); |
853 | 832 |
854 bool bNumber; | 833 bool bNumber; |
855 CFX_ByteString objnum = m_parser.m_pSyntax->GetNextWord(&bNumber); | 834 CFX_ByteString objnum = m_parser.m_pSyntax->GetNextWord(&bNumber); |
856 if (!bNumber) | 835 if (!bNumber) |
857 return -1; | 836 return -1; |
858 | 837 |
859 uint32_t objNum = FXSYS_atoui(objnum.c_str()); | 838 uint32_t objNum = FXSYS_atoui(objnum.c_str()); |
860 CPDF_Object* pObj = m_parser.ParseIndirectObjectAt(nullptr, 0, objNum); | 839 std::unique_ptr<CPDF_Object> pObj = |
| 840 m_parser.ParseIndirectObjectAt(nullptr, 0, objNum); |
| 841 |
861 if (!pObj) { | 842 if (!pObj) { |
862 m_Pos += m_parser.m_pSyntax->SavePos(); | 843 m_Pos += m_parser.m_pSyntax->SavePos(); |
863 return 0; | 844 return 0; |
864 } | 845 } |
865 | 846 |
866 CPDF_Dictionary* pDict = pObj->GetDict(); | 847 CPDF_Dictionary* pDict = pObj->GetDict(); |
867 CPDF_Name* pName = ToName(pDict ? pDict->GetObjectFor("Type") : nullptr); | 848 CPDF_Name* pName = ToName(pDict ? pDict->GetObjectFor("Type") : nullptr); |
868 if (pName) { | 849 if (pName && pName->GetString() == "XRef") { |
869 if (pName->GetString() == "XRef") { | 850 m_Pos += m_parser.m_pSyntax->SavePos(); |
870 m_Pos += m_parser.m_pSyntax->SavePos(); | 851 xref_offset = pObj->GetDict()->GetIntegerFor("Prev"); |
871 xref_offset = pObj->GetDict()->GetIntegerFor("Prev"); | 852 return 1; |
872 delete pObj; | |
873 return 1; | |
874 } | |
875 } | 853 } |
876 delete pObj; | |
877 return -1; | 854 return -1; |
878 } | 855 } |
879 pHints->AddSegment(m_Pos, req_size); | 856 pHints->AddSegment(m_Pos, req_size); |
880 return 0; | 857 return 0; |
881 } | 858 } |
882 | 859 |
883 void CPDF_DataAvail::SetStartOffset(FX_FILESIZE dwOffset) { | 860 void CPDF_DataAvail::SetStartOffset(FX_FILESIZE dwOffset) { |
884 m_Pos = dwOffset; | 861 m_Pos = dwOffset; |
885 } | 862 } |
886 | 863 |
(...skipping 274 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1161 m_docStatus = PDF_DATAAVAIL_PAGE; | 1138 m_docStatus = PDF_DATAAVAIL_PAGE; |
1162 return true; | 1139 return true; |
1163 } | 1140 } |
1164 } | 1141 } |
1165 } | 1142 } |
1166 | 1143 |
1167 bool CPDF_DataAvail::CheckArrayPageNode(uint32_t dwPageNo, | 1144 bool CPDF_DataAvail::CheckArrayPageNode(uint32_t dwPageNo, |
1168 PageNode* pPageNode, | 1145 PageNode* pPageNode, |
1169 DownloadHints* pHints) { | 1146 DownloadHints* pHints) { |
1170 bool bExist = false; | 1147 bool bExist = false; |
1171 CPDF_Object* pPages = GetObject(dwPageNo, pHints, &bExist); | 1148 std::unique_ptr<CPDF_Object> pPages = GetObject(dwPageNo, pHints, &bExist); |
1172 if (!bExist) { | 1149 if (!bExist) { |
1173 m_docStatus = PDF_DATAAVAIL_ERROR; | 1150 m_docStatus = PDF_DATAAVAIL_ERROR; |
1174 return false; | 1151 return false; |
1175 } | 1152 } |
1176 | 1153 |
1177 if (!pPages) { | 1154 if (!pPages) { |
1178 if (m_docStatus == PDF_DATAAVAIL_ERROR) { | 1155 if (m_docStatus == PDF_DATAAVAIL_ERROR) { |
1179 m_docStatus = PDF_DATAAVAIL_ERROR; | 1156 m_docStatus = PDF_DATAAVAIL_ERROR; |
1180 return false; | 1157 return false; |
1181 } | 1158 } |
1182 return false; | 1159 return false; |
1183 } | 1160 } |
1184 | 1161 |
1185 CPDF_Array* pArray = pPages->AsArray(); | 1162 CPDF_Array* pArray = pPages->AsArray(); |
1186 if (!pArray) { | 1163 if (!pArray) { |
1187 delete pPages; | |
1188 m_docStatus = PDF_DATAAVAIL_ERROR; | 1164 m_docStatus = PDF_DATAAVAIL_ERROR; |
1189 return false; | 1165 return false; |
1190 } | 1166 } |
1191 | 1167 |
1192 pPageNode->m_type = PDF_PAGENODE_PAGES; | 1168 pPageNode->m_type = PDF_PAGENODE_PAGES; |
1193 for (size_t i = 0; i < pArray->GetCount(); ++i) { | 1169 for (size_t i = 0; i < pArray->GetCount(); ++i) { |
1194 CPDF_Reference* pKid = ToReference(pArray->GetObjectAt(i)); | 1170 CPDF_Reference* pKid = ToReference(pArray->GetObjectAt(i)); |
1195 if (!pKid) | 1171 if (!pKid) |
1196 continue; | 1172 continue; |
1197 | 1173 |
1198 PageNode* pNode = new PageNode(); | 1174 PageNode* pNode = new PageNode(); |
1199 pPageNode->m_childNode.Add(pNode); | 1175 pPageNode->m_childNode.Add(pNode); |
1200 pNode->m_dwPageNo = pKid->GetRefObjNum(); | 1176 pNode->m_dwPageNo = pKid->GetRefObjNum(); |
1201 } | 1177 } |
1202 delete pPages; | |
1203 return true; | 1178 return true; |
1204 } | 1179 } |
1205 | 1180 |
1206 bool CPDF_DataAvail::CheckUnkownPageNode(uint32_t dwPageNo, | 1181 bool CPDF_DataAvail::CheckUnkownPageNode(uint32_t dwPageNo, |
1207 PageNode* pPageNode, | 1182 PageNode* pPageNode, |
1208 DownloadHints* pHints) { | 1183 DownloadHints* pHints) { |
1209 bool bExist = false; | 1184 bool bExist = false; |
1210 CPDF_Object* pPage = GetObject(dwPageNo, pHints, &bExist); | 1185 std::unique_ptr<CPDF_Object> pPage = GetObject(dwPageNo, pHints, &bExist); |
1211 if (!bExist) { | 1186 if (!bExist) { |
1212 m_docStatus = PDF_DATAAVAIL_ERROR; | 1187 m_docStatus = PDF_DATAAVAIL_ERROR; |
1213 return false; | 1188 return false; |
1214 } | 1189 } |
1215 | 1190 |
1216 if (!pPage) { | 1191 if (!pPage) { |
1217 if (m_docStatus == PDF_DATAAVAIL_ERROR) | 1192 if (m_docStatus == PDF_DATAAVAIL_ERROR) |
1218 m_docStatus = PDF_DATAAVAIL_ERROR; | 1193 m_docStatus = PDF_DATAAVAIL_ERROR; |
1219 return false; | 1194 return false; |
1220 } | 1195 } |
1221 | 1196 |
1222 if (pPage->IsArray()) { | 1197 if (pPage->IsArray()) { |
1223 pPageNode->m_dwPageNo = dwPageNo; | 1198 pPageNode->m_dwPageNo = dwPageNo; |
1224 pPageNode->m_type = PDF_PAGENODE_ARRAY; | 1199 pPageNode->m_type = PDF_PAGENODE_ARRAY; |
1225 delete pPage; | |
1226 return true; | 1200 return true; |
1227 } | 1201 } |
1228 | 1202 |
1229 if (!pPage->IsDictionary()) { | 1203 if (!pPage->IsDictionary()) { |
1230 delete pPage; | |
1231 m_docStatus = PDF_DATAAVAIL_ERROR; | 1204 m_docStatus = PDF_DATAAVAIL_ERROR; |
1232 return false; | 1205 return false; |
1233 } | 1206 } |
1234 | 1207 |
1235 pPageNode->m_dwPageNo = dwPageNo; | 1208 pPageNode->m_dwPageNo = dwPageNo; |
1236 CPDF_Dictionary* pDict = pPage->GetDict(); | 1209 CPDF_Dictionary* pDict = pPage->GetDict(); |
1237 CFX_ByteString type = pDict->GetStringFor("Type"); | 1210 CFX_ByteString type = pDict->GetStringFor("Type"); |
1238 if (type == "Pages") { | 1211 if (type == "Pages") { |
1239 pPageNode->m_type = PDF_PAGENODE_PAGES; | 1212 pPageNode->m_type = PDF_PAGENODE_PAGES; |
1240 CPDF_Object* pKids = pDict->GetObjectFor("Kids"); | 1213 CPDF_Object* pKids = pDict->GetObjectFor("Kids"); |
(...skipping 20 matching lines...) Expand all Loading... |
1261 pPageNode->m_childNode.Add(pNode); | 1234 pPageNode->m_childNode.Add(pNode); |
1262 pNode->m_dwPageNo = pKid->GetRefObjNum(); | 1235 pNode->m_dwPageNo = pKid->GetRefObjNum(); |
1263 } | 1236 } |
1264 } break; | 1237 } break; |
1265 default: | 1238 default: |
1266 break; | 1239 break; |
1267 } | 1240 } |
1268 } else if (type == "Page") { | 1241 } else if (type == "Page") { |
1269 pPageNode->m_type = PDF_PAGENODE_PAGE; | 1242 pPageNode->m_type = PDF_PAGENODE_PAGE; |
1270 } else { | 1243 } else { |
1271 delete pPage; | |
1272 m_docStatus = PDF_DATAAVAIL_ERROR; | 1244 m_docStatus = PDF_DATAAVAIL_ERROR; |
1273 return false; | 1245 return false; |
1274 } | 1246 } |
1275 delete pPage; | |
1276 return true; | 1247 return true; |
1277 } | 1248 } |
1278 | 1249 |
1279 bool CPDF_DataAvail::CheckPageNode(CPDF_DataAvail::PageNode& pageNodes, | 1250 bool CPDF_DataAvail::CheckPageNode(CPDF_DataAvail::PageNode& pageNodes, |
1280 int32_t iPage, | 1251 int32_t iPage, |
1281 int32_t& iCount, | 1252 int32_t& iCount, |
1282 DownloadHints* pHints, | 1253 DownloadHints* pHints, |
1283 int level) { | 1254 int level) { |
1284 if (level >= kMaxPageRecursionDepth) | 1255 if (level >= kMaxPageRecursionDepth) |
1285 return false; | 1256 return false; |
(...skipping 56 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1342 } | 1313 } |
1343 m_docStatus = PDF_DATAAVAIL_ERROR; | 1314 m_docStatus = PDF_DATAAVAIL_ERROR; |
1344 return true; | 1315 return true; |
1345 } | 1316 } |
1346 int32_t iCount = -1; | 1317 int32_t iCount = -1; |
1347 return CheckPageNode(m_pageNodes, iPage, iCount, pHints, 0); | 1318 return CheckPageNode(m_pageNodes, iPage, iCount, pHints, 0); |
1348 } | 1319 } |
1349 | 1320 |
1350 bool CPDF_DataAvail::CheckPageCount(DownloadHints* pHints) { | 1321 bool CPDF_DataAvail::CheckPageCount(DownloadHints* pHints) { |
1351 bool bExist = false; | 1322 bool bExist = false; |
1352 CPDF_Object* pPages = GetObject(m_PagesObjNum, pHints, &bExist); | 1323 std::unique_ptr<CPDF_Object> pPages = |
| 1324 GetObject(m_PagesObjNum, pHints, &bExist); |
1353 if (!bExist) { | 1325 if (!bExist) { |
1354 m_docStatus = PDF_DATAAVAIL_ERROR; | 1326 m_docStatus = PDF_DATAAVAIL_ERROR; |
1355 return false; | 1327 return false; |
1356 } | 1328 } |
1357 | 1329 |
1358 if (!pPages) | 1330 if (!pPages) |
1359 return false; | 1331 return false; |
1360 | 1332 |
1361 CPDF_Dictionary* pPagesDict = pPages->GetDict(); | 1333 CPDF_Dictionary* pPagesDict = pPages->GetDict(); |
1362 if (!pPagesDict) { | 1334 if (!pPagesDict) { |
1363 delete pPages; | |
1364 m_docStatus = PDF_DATAAVAIL_ERROR; | 1335 m_docStatus = PDF_DATAAVAIL_ERROR; |
1365 return false; | 1336 return false; |
1366 } | 1337 } |
1367 | 1338 |
1368 if (!pPagesDict->KeyExist("Kids")) { | 1339 if (!pPagesDict->KeyExist("Kids")) |
1369 delete pPages; | |
1370 return true; | 1340 return true; |
1371 } | |
1372 | 1341 |
1373 int count = pPagesDict->GetIntegerFor("Count"); | 1342 return pPagesDict->GetIntegerFor("Count") > 0; |
1374 if (count > 0) { | |
1375 delete pPages; | |
1376 return true; | |
1377 } | |
1378 | |
1379 delete pPages; | |
1380 return false; | |
1381 } | 1343 } |
1382 | 1344 |
1383 bool CPDF_DataAvail::LoadDocPages(DownloadHints* pHints) { | 1345 bool CPDF_DataAvail::LoadDocPages(DownloadHints* pHints) { |
1384 if (!CheckUnkownPageNode(m_PagesObjNum, &m_pageNodes, pHints)) | 1346 if (!CheckUnkownPageNode(m_PagesObjNum, &m_pageNodes, pHints)) |
1385 return false; | 1347 return false; |
1386 | 1348 |
1387 if (CheckPageCount(pHints)) { | 1349 if (CheckPageCount(pHints)) { |
1388 m_docStatus = PDF_DATAAVAIL_PAGE; | 1350 m_docStatus = PDF_DATAAVAIL_PAGE; |
1389 return true; | 1351 return true; |
1390 } | 1352 } |
(...skipping 285 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1676 FX_FILESIZE szPageLength = 0; | 1638 FX_FILESIZE szPageLength = 0; |
1677 uint32_t dwObjNum = 0; | 1639 uint32_t dwObjNum = 0; |
1678 const bool bPagePosGot = m_pHintTables->GetPagePos(index, &szPageStartPos, | 1640 const bool bPagePosGot = m_pHintTables->GetPagePos(index, &szPageStartPos, |
1679 &szPageLength, &dwObjNum); | 1641 &szPageLength, &dwObjNum); |
1680 if (!bPagePosGot || !dwObjNum) | 1642 if (!bPagePosGot || !dwObjNum) |
1681 return nullptr; | 1643 return nullptr; |
1682 // We should say to the document, which object is the page. | 1644 // We should say to the document, which object is the page. |
1683 m_pDocument->SetPageObjNum(index, dwObjNum); | 1645 m_pDocument->SetPageObjNum(index, dwObjNum); |
1684 // Page object already can be parsed in document. | 1646 // Page object already can be parsed in document. |
1685 if (!m_pDocument->GetIndirectObject(dwObjNum)) { | 1647 if (!m_pDocument->GetIndirectObject(dwObjNum)) { |
1686 m_syntaxParser.InitParser(m_pFileRead, (uint32_t)szPageStartPos); | 1648 m_syntaxParser.InitParser( |
| 1649 m_pFileRead, pdfium::base::checked_cast<uint32_t>(szPageStartPos)); |
1687 m_pDocument->ReplaceIndirectObjectIfHigherGeneration( | 1650 m_pDocument->ReplaceIndirectObjectIfHigherGeneration( |
1688 dwObjNum, pdfium::WrapUnique<CPDF_Object>( | 1651 dwObjNum, ParseIndirectObjectAt(0, dwObjNum, m_pDocument)); |
1689 ParseIndirectObjectAt(0, dwObjNum, m_pDocument))); | |
1690 } | 1652 } |
1691 return m_pDocument->GetPage(index); | 1653 return m_pDocument->GetPage(index); |
1692 } | 1654 } |
1693 | 1655 |
1694 CPDF_DataAvail::DocFormStatus CPDF_DataAvail::IsFormAvail( | 1656 CPDF_DataAvail::DocFormStatus CPDF_DataAvail::IsFormAvail( |
1695 DownloadHints* pHints) { | 1657 DownloadHints* pHints) { |
1696 if (!m_pDocument) | 1658 if (!m_pDocument) |
1697 return FormAvailable; | 1659 return FormAvailable; |
1698 | 1660 |
1699 if (!m_bLinearizedFormParamLoad) { | 1661 if (!m_bLinearizedFormParamLoad) { |
(...skipping 26 matching lines...) Expand all Loading... |
1726 return FormAvailable; | 1688 return FormAvailable; |
1727 } | 1689 } |
1728 | 1690 |
1729 CPDF_DataAvail::PageNode::PageNode() : m_type(PDF_PAGENODE_UNKNOWN) {} | 1691 CPDF_DataAvail::PageNode::PageNode() : m_type(PDF_PAGENODE_UNKNOWN) {} |
1730 | 1692 |
1731 CPDF_DataAvail::PageNode::~PageNode() { | 1693 CPDF_DataAvail::PageNode::~PageNode() { |
1732 for (int32_t i = 0; i < m_childNode.GetSize(); ++i) | 1694 for (int32_t i = 0; i < m_childNode.GetSize(); ++i) |
1733 delete m_childNode[i]; | 1695 delete m_childNode[i]; |
1734 m_childNode.RemoveAll(); | 1696 m_childNode.RemoveAll(); |
1735 } | 1697 } |
OLD | NEW |