Chromium Code Reviews| 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_name.h" | 18 #include "core/fpdfapi/parser/cpdf_name.h" |
| 19 #include "core/fpdfapi/parser/cpdf_number.h" | 19 #include "core/fpdfapi/parser/cpdf_number.h" |
| 20 #include "core/fpdfapi/parser/cpdf_reference.h" | 20 #include "core/fpdfapi/parser/cpdf_reference.h" |
| 21 #include "core/fpdfapi/parser/cpdf_stream.h" | 21 #include "core/fpdfapi/parser/cpdf_stream.h" |
| 22 #include "core/fpdfapi/parser/fpdf_parser_utility.h" | 22 #include "core/fpdfapi/parser/fpdf_parser_utility.h" |
| 23 #include "core/fxcrt/fx_ext.h" | 23 #include "core/fxcrt/fx_ext.h" |
| 24 #include "core/fxcrt/fx_safe_types.h" | 24 #include "core/fxcrt/fx_safe_types.h" |
| 25 #include "third_party/base/numerics/safe_conversions.h" | |
| 25 #include "third_party/base/stl_util.h" | 26 #include "third_party/base/stl_util.h" |
| 26 | 27 |
| 27 CPDF_DataAvail::FileAvail::~FileAvail() {} | 28 CPDF_DataAvail::FileAvail::~FileAvail() {} |
| 28 | 29 |
| 29 CPDF_DataAvail::DownloadHints::~DownloadHints() {} | 30 CPDF_DataAvail::DownloadHints::~DownloadHints() {} |
| 30 | 31 |
| 31 // static | 32 // static |
| 32 int CPDF_DataAvail::s_CurrentDataAvailRecursionDepth = 0; | 33 int CPDF_DataAvail::s_CurrentDataAvailRecursionDepth = 0; |
| 33 | 34 |
| 34 CPDF_DataAvail::CPDF_DataAvail(FileAvail* pFileAvail, | 35 CPDF_DataAvail::CPDF_DataAvail(FileAvail* pFileAvail, |
| (...skipping 24 matching lines...) Expand all Loading... | |
| 59 m_bLinearized = false; | 60 m_bLinearized = false; |
| 60 m_bPagesLoad = false; | 61 m_bPagesLoad = false; |
| 61 m_bPagesTreeLoad = false; | 62 m_bPagesTreeLoad = false; |
| 62 m_bMainXRefLoadedOK = false; | 63 m_bMainXRefLoadedOK = false; |
| 63 m_bAnnotsLoad = false; | 64 m_bAnnotsLoad = false; |
| 64 m_bHaveAcroForm = false; | 65 m_bHaveAcroForm = false; |
| 65 m_bAcroFormLoad = false; | 66 m_bAcroFormLoad = false; |
| 66 m_bPageLoadedOK = false; | 67 m_bPageLoadedOK = false; |
| 67 m_bNeedDownLoadResource = false; | 68 m_bNeedDownLoadResource = false; |
| 68 m_bLinearizedFormParamLoad = false; | 69 m_bLinearizedFormParamLoad = false; |
| 69 m_pLinearized = nullptr; | |
| 70 m_pRoot = nullptr; | |
| 71 m_pTrailer = nullptr; | 70 m_pTrailer = nullptr; |
| 72 m_pCurrentParser = nullptr; | 71 m_pCurrentParser = nullptr; |
| 73 m_pAcroForm = nullptr; | 72 m_pAcroForm = nullptr; |
| 74 m_pPageDict = nullptr; | 73 m_pPageDict = nullptr; |
| 75 m_pPageResource = nullptr; | 74 m_pPageResource = nullptr; |
| 76 m_docStatus = PDF_DATAAVAIL_HEADER; | 75 m_docStatus = PDF_DATAAVAIL_HEADER; |
| 77 m_parser.m_bOwnFileRead = false; | 76 m_parser.m_bOwnFileRead = false; |
| 78 m_bTotalLoadPageTree = false; | 77 m_bTotalLoadPageTree = false; |
| 79 m_bCurPageDictLoadOK = false; | 78 m_bCurPageDictLoadOK = false; |
| 80 m_bLinearedDataOK = false; | 79 m_bLinearedDataOK = false; |
| 81 m_bSupportHintTable = bSupportHintTable; | 80 m_bSupportHintTable = bSupportHintTable; |
| 82 } | 81 } |
| 83 | 82 |
| 84 CPDF_DataAvail::~CPDF_DataAvail() { | 83 CPDF_DataAvail::~CPDF_DataAvail() { |
| 85 m_pHintTables.reset(); | 84 m_pHintTables.reset(); |
| 86 delete m_pLinearized; | |
| 87 delete m_pRoot; | |
| 88 delete m_pTrailer; | 85 delete m_pTrailer; |
| 89 | 86 |
| 90 for (CPDF_Object* pObject : m_arrayAcroforms) | 87 for (CPDF_Object* pObject : m_arrayAcroforms) |
| 91 delete pObject; | 88 delete pObject; |
| 92 } | 89 } |
| 93 | 90 |
| 94 void CPDF_DataAvail::SetDocument(CPDF_Document* pDoc) { | 91 void CPDF_DataAvail::SetDocument(CPDF_Document* pDoc) { |
| 95 m_pDocument = pDoc; | 92 m_pDocument = pDoc; |
| 96 } | 93 } |
| 97 | 94 |
| (...skipping 128 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 226 | 223 |
| 227 for (CPDF_Object* pObject : m_arrayAcroforms) | 224 for (CPDF_Object* pObject : m_arrayAcroforms) |
| 228 delete pObject; | 225 delete pObject; |
| 229 | 226 |
| 230 m_arrayAcroforms.clear(); | 227 m_arrayAcroforms.clear(); |
| 231 return true; | 228 return true; |
| 232 } | 229 } |
| 233 | 230 |
| 234 bool CPDF_DataAvail::CheckAcroForm(DownloadHints* pHints) { | 231 bool CPDF_DataAvail::CheckAcroForm(DownloadHints* pHints) { |
| 235 bool bExist = false; | 232 bool bExist = false; |
| 236 m_pAcroForm = GetObject(m_dwAcroFormObjNum, pHints, &bExist); | 233 m_pAcroForm = GetObject(m_dwAcroFormObjNum, pHints, &bExist).release(); |
| 237 if (!bExist) { | 234 if (!bExist) { |
| 238 m_docStatus = PDF_DATAAVAIL_PAGETREE; | 235 m_docStatus = PDF_DATAAVAIL_PAGETREE; |
| 239 return true; | 236 return true; |
| 240 } | 237 } |
| 241 | 238 |
| 242 if (!m_pAcroForm) { | 239 if (!m_pAcroForm) { |
| 243 if (m_docStatus == PDF_DATAAVAIL_ERROR) { | 240 if (m_docStatus == PDF_DATAAVAIL_ERROR) { |
| 244 m_docStatus = PDF_DATAAVAIL_LOADALLFILE; | 241 m_docStatus = PDF_DATAAVAIL_LOADALLFILE; |
| 245 return true; | 242 return true; |
| 246 } | 243 } |
| (...skipping 89 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 336 return false; | 333 return false; |
| 337 } | 334 } |
| 338 | 335 |
| 339 m_dwRootObjNum = m_parser.GetRootObjNum(); | 336 m_dwRootObjNum = m_parser.GetRootObjNum(); |
| 340 m_dwInfoObjNum = m_parser.GetInfoObjNum(); | 337 m_dwInfoObjNum = m_parser.GetInfoObjNum(); |
| 341 m_pCurrentParser = &m_parser; | 338 m_pCurrentParser = &m_parser; |
| 342 m_docStatus = PDF_DATAAVAIL_ROOT; | 339 m_docStatus = PDF_DATAAVAIL_ROOT; |
| 343 return true; | 340 return true; |
| 344 } | 341 } |
| 345 | 342 |
| 346 CPDF_Object* CPDF_DataAvail::GetObject(uint32_t objnum, | 343 std::unique_ptr<CPDF_Object> CPDF_DataAvail::GetObject(uint32_t objnum, |
| 347 DownloadHints* pHints, | 344 DownloadHints* pHints, |
| 348 bool* pExistInFile) { | 345 bool* pExistInFile) { |
| 349 CPDF_Object* pRet = nullptr; | |
| 350 uint32_t size = 0; | 346 uint32_t size = 0; |
| 351 FX_FILESIZE offset = 0; | 347 FX_FILESIZE offset = 0; |
| 352 CPDF_Parser* pParser = nullptr; | 348 CPDF_Parser* pParser = nullptr; |
| 353 | 349 |
| 354 if (pExistInFile) | 350 if (pExistInFile) |
| 355 *pExistInFile = true; | 351 *pExistInFile = true; |
| 356 | 352 |
| 357 if (m_pDocument) { | 353 if (m_pDocument) { |
| 358 size = GetObjectSize(objnum, offset); | 354 size = GetObjectSize(objnum, offset); |
| 359 pParser = m_pDocument->GetParser(); | 355 pParser = m_pDocument->GetParser(); |
| 360 } else { | 356 } else { |
| 361 size = (uint32_t)m_parser.GetObjectSize(objnum); | 357 size = (uint32_t)m_parser.GetObjectSize(objnum); |
| 362 offset = m_parser.GetObjectOffset(objnum); | 358 offset = m_parser.GetObjectOffset(objnum); |
| 363 pParser = &m_parser; | 359 pParser = &m_parser; |
| 364 } | 360 } |
| 365 | 361 |
| 366 if (!IsDataAvail(offset, size, pHints)) | 362 if (!IsDataAvail(offset, size, pHints)) |
| 367 return nullptr; | 363 return nullptr; |
| 368 | 364 |
| 365 std::unique_ptr<CPDF_Object> pRet; | |
| 369 if (pParser) | 366 if (pParser) |
| 370 pRet = pParser->ParseIndirectObject(nullptr, objnum); | 367 pRet = pParser->ParseIndirectObject(nullptr, objnum); |
| 371 | 368 |
| 372 if (!pRet && pExistInFile) | 369 if (!pRet && pExistInFile) |
| 373 *pExistInFile = false; | 370 *pExistInFile = false; |
| 374 | 371 |
| 375 return pRet; | 372 return pRet; |
| 376 } | 373 } |
| 377 | 374 |
| 378 bool CPDF_DataAvail::CheckInfo(DownloadHints* pHints) { | 375 bool CPDF_DataAvail::CheckInfo(DownloadHints* pHints) { |
| 379 bool bExist = false; | 376 bool bExist = false; |
| 380 CPDF_Object* pInfo = GetObject(m_dwInfoObjNum, pHints, &bExist); | 377 std::unique_ptr<CPDF_Object> pInfo = |
| 381 if (!bExist) { | 378 GetObject(m_dwInfoObjNum, pHints, &bExist); |
| 382 m_docStatus = | 379 if (bExist && !pInfo) { |
| 383 (m_bHaveAcroForm ? PDF_DATAAVAIL_ACROFORM : PDF_DATAAVAIL_PAGETREE); | |
| 384 return true; | |
| 385 } | |
| 386 | |
| 387 if (!pInfo) { | |
| 388 if (m_docStatus == PDF_DATAAVAIL_ERROR) { | 380 if (m_docStatus == PDF_DATAAVAIL_ERROR) { |
| 389 m_docStatus = PDF_DATAAVAIL_LOADALLFILE; | 381 m_docStatus = PDF_DATAAVAIL_LOADALLFILE; |
| 390 return true; | 382 return true; |
| 391 } | 383 } |
| 392 | |
| 393 if (m_Pos == m_dwFileLen) | 384 if (m_Pos == m_dwFileLen) |
| 394 m_docStatus = PDF_DATAAVAIL_ERROR; | 385 m_docStatus = PDF_DATAAVAIL_ERROR; |
| 395 return false; | 386 return false; |
| 396 } | 387 } |
| 397 | |
| 398 delete pInfo; | |
| 399 m_docStatus = | 388 m_docStatus = |
| 400 (m_bHaveAcroForm ? PDF_DATAAVAIL_ACROFORM : PDF_DATAAVAIL_PAGETREE); | 389 m_bHaveAcroForm ? PDF_DATAAVAIL_ACROFORM : PDF_DATAAVAIL_PAGETREE; |
| 401 | |
| 402 return true; | 390 return true; |
| 403 } | 391 } |
| 404 | 392 |
| 405 bool CPDF_DataAvail::CheckRoot(DownloadHints* pHints) { | 393 bool CPDF_DataAvail::CheckRoot(DownloadHints* pHints) { |
| 406 bool bExist = false; | 394 bool bExist = false; |
| 407 m_pRoot = GetObject(m_dwRootObjNum, pHints, &bExist); | 395 m_pRoot = GetObject(m_dwRootObjNum, pHints, &bExist); |
| 408 if (!bExist) { | 396 if (!bExist) { |
| 409 m_docStatus = PDF_DATAAVAIL_LOADALLFILE; | 397 m_docStatus = PDF_DATAAVAIL_LOADALLFILE; |
| 410 return true; | 398 return true; |
| 411 } | 399 } |
| (...skipping 57 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 469 void CPDF_DataAvail::ResetFirstCheck(uint32_t dwPage) { | 457 void CPDF_DataAvail::ResetFirstCheck(uint32_t dwPage) { |
| 470 m_pageMapCheckState.erase(dwPage); | 458 m_pageMapCheckState.erase(dwPage); |
| 471 } | 459 } |
| 472 | 460 |
| 473 bool CPDF_DataAvail::CheckPage(DownloadHints* pHints) { | 461 bool CPDF_DataAvail::CheckPage(DownloadHints* pHints) { |
| 474 uint32_t iPageObjs = m_PageObjList.GetSize(); | 462 uint32_t iPageObjs = m_PageObjList.GetSize(); |
| 475 CFX_ArrayTemplate<uint32_t> UnavailObjList; | 463 CFX_ArrayTemplate<uint32_t> UnavailObjList; |
| 476 for (uint32_t i = 0; i < iPageObjs; ++i) { | 464 for (uint32_t i = 0; i < iPageObjs; ++i) { |
| 477 uint32_t dwPageObjNum = m_PageObjList.GetAt(i); | 465 uint32_t dwPageObjNum = m_PageObjList.GetAt(i); |
| 478 bool bExist = false; | 466 bool bExist = false; |
| 479 CPDF_Object* pObj = GetObject(dwPageObjNum, pHints, &bExist); | 467 std::unique_ptr<CPDF_Object> pObj = |
| 468 GetObject(dwPageObjNum, pHints, &bExist); | |
| 480 if (!pObj) { | 469 if (!pObj) { |
| 481 if (bExist) | 470 if (bExist) |
| 482 UnavailObjList.Add(dwPageObjNum); | 471 UnavailObjList.Add(dwPageObjNum); |
| 483 continue; | 472 continue; |
| 484 } | 473 } |
| 485 | 474 |
| 486 CPDF_Array* pArray = ToArray(pObj); | 475 CPDF_Array* pArray = ToArray(pObj.get()); |
| 487 if (pArray) { | 476 if (pArray) { |
| 488 for (CPDF_Object* pArrayObj : *pArray) { | 477 for (CPDF_Object* pArrayObj : *pArray) { |
| 489 if (CPDF_Reference* pRef = ToReference(pArrayObj)) | 478 if (CPDF_Reference* pRef = ToReference(pArrayObj)) |
| 490 UnavailObjList.Add(pRef->GetRefObjNum()); | 479 UnavailObjList.Add(pRef->GetRefObjNum()); |
| 491 } | 480 } |
| 492 } | 481 } |
| 493 | 482 |
| 494 if (!pObj->IsDictionary()) { | 483 if (!pObj->IsDictionary()) { |
| 495 delete pObj; | |
| 496 continue; | 484 continue; |
| 497 } | 485 } |
| 498 | 486 |
| 499 CFX_ByteString type = pObj->GetDict()->GetStringFor("Type"); | 487 CFX_ByteString type = pObj->GetDict()->GetStringFor("Type"); |
| 500 if (type == "Pages") { | 488 if (type == "Pages") { |
| 501 m_PagesArray.push_back(pObj); | 489 m_PagesArray.push_back(std::move(pObj)); |
| 502 continue; | 490 continue; |
| 503 } | 491 } |
| 504 delete pObj; | |
| 505 } | 492 } |
| 506 | 493 |
| 507 m_PageObjList.RemoveAll(); | 494 m_PageObjList.RemoveAll(); |
| 508 if (UnavailObjList.GetSize()) { | 495 if (UnavailObjList.GetSize()) { |
| 509 m_PageObjList.Append(UnavailObjList); | 496 m_PageObjList.Append(UnavailObjList); |
| 510 return false; | 497 return false; |
| 511 } | 498 } |
| 512 | 499 |
| 513 uint32_t iPages = m_PagesArray.size(); | 500 uint32_t iPages = m_PagesArray.size(); |
| 514 for (uint32_t i = 0; i < iPages; i++) { | 501 for (uint32_t i = 0; i < iPages; i++) { |
| 515 CPDF_Object* pPages = m_PagesArray[i]; | 502 std::unique_ptr<CPDF_Object> pPages = std::move(m_PagesArray[i]); |
| 516 if (!pPages) | 503 if (pPages && !GetPageKids(m_pCurrentParser, pPages.get())) { |
| 517 continue; | |
| 518 | |
| 519 if (!GetPageKids(m_pCurrentParser, pPages)) { | |
| 520 delete pPages; | |
| 521 while (++i < iPages) | |
| 522 delete m_PagesArray[i]; | |
| 523 | |
| 524 m_PagesArray.clear(); | 504 m_PagesArray.clear(); |
| 525 m_docStatus = PDF_DATAAVAIL_ERROR; | 505 m_docStatus = PDF_DATAAVAIL_ERROR; |
| 526 return false; | 506 return false; |
| 527 } | 507 } |
| 528 delete pPages; | |
| 529 } | 508 } |
| 530 | |
| 531 m_PagesArray.clear(); | 509 m_PagesArray.clear(); |
| 532 if (!m_PageObjList.GetSize()) | 510 if (!m_PageObjList.GetSize()) |
| 533 m_docStatus = PDF_DATAAVAIL_DONE; | 511 m_docStatus = PDF_DATAAVAIL_DONE; |
| 512 | |
| 534 return true; | 513 return true; |
| 535 } | 514 } |
| 536 | 515 |
| 537 bool CPDF_DataAvail::GetPageKids(CPDF_Parser* pParser, CPDF_Object* pPages) { | 516 bool CPDF_DataAvail::GetPageKids(CPDF_Parser* pParser, CPDF_Object* pPages) { |
| 538 if (!pParser) { | 517 if (!pParser) { |
| 539 m_docStatus = PDF_DATAAVAIL_ERROR; | 518 m_docStatus = PDF_DATAAVAIL_ERROR; |
| 540 return false; | 519 return false; |
| 541 } | 520 } |
| 542 | 521 |
| 543 CPDF_Dictionary* pDict = pPages->GetDict(); | 522 CPDF_Dictionary* pDict = pPages->GetDict(); |
| (...skipping 14 matching lines...) Expand all Loading... | |
| 558 } break; | 537 } break; |
| 559 default: | 538 default: |
| 560 m_docStatus = PDF_DATAAVAIL_ERROR; | 539 m_docStatus = PDF_DATAAVAIL_ERROR; |
| 561 return false; | 540 return false; |
| 562 } | 541 } |
| 563 return true; | 542 return true; |
| 564 } | 543 } |
| 565 | 544 |
| 566 bool CPDF_DataAvail::CheckPages(DownloadHints* pHints) { | 545 bool CPDF_DataAvail::CheckPages(DownloadHints* pHints) { |
| 567 bool bExist = false; | 546 bool bExist = false; |
| 568 CPDF_Object* pPages = GetObject(m_PagesObjNum, pHints, &bExist); | 547 std::unique_ptr<CPDF_Object> pPages = |
| 548 GetObject(m_PagesObjNum, pHints, &bExist); | |
| 569 if (!bExist) { | 549 if (!bExist) { |
| 570 m_docStatus = PDF_DATAAVAIL_LOADALLFILE; | 550 m_docStatus = PDF_DATAAVAIL_LOADALLFILE; |
| 571 return true; | 551 return true; |
| 572 } | 552 } |
| 573 | 553 |
| 574 if (!pPages) { | 554 if (!pPages) { |
| 575 if (m_docStatus == PDF_DATAAVAIL_ERROR) { | 555 if (m_docStatus == PDF_DATAAVAIL_ERROR) { |
| 576 m_docStatus = PDF_DATAAVAIL_LOADALLFILE; | 556 m_docStatus = PDF_DATAAVAIL_LOADALLFILE; |
| 577 return true; | 557 return true; |
| 578 } | 558 } |
| 579 return false; | 559 return false; |
| 580 } | 560 } |
| 581 | 561 |
| 582 if (!GetPageKids(m_pCurrentParser, pPages)) { | 562 if (!GetPageKids(m_pCurrentParser, pPages.get())) { |
| 583 delete pPages; | |
| 584 m_docStatus = PDF_DATAAVAIL_ERROR; | 563 m_docStatus = PDF_DATAAVAIL_ERROR; |
| 585 return false; | 564 return false; |
| 586 } | 565 } |
| 587 | 566 |
| 588 delete pPages; | |
| 589 m_docStatus = PDF_DATAAVAIL_PAGE; | 567 m_docStatus = PDF_DATAAVAIL_PAGE; |
| 590 return true; | 568 return true; |
| 591 } | 569 } |
| 592 | 570 |
| 593 bool CPDF_DataAvail::CheckHeader(DownloadHints* pHints) { | 571 bool CPDF_DataAvail::CheckHeader(DownloadHints* pHints) { |
| 594 ASSERT(m_dwFileLen >= 0); | 572 ASSERT(m_dwFileLen >= 0); |
| 595 const uint32_t kReqSize = std::min(static_cast<uint32_t>(m_dwFileLen), 1024U); | 573 const uint32_t kReqSize = std::min(static_cast<uint32_t>(m_dwFileLen), 1024U); |
| 596 | 574 |
| 597 if (m_pFileAvail->IsDataAvail(0, kReqSize)) { | 575 if (m_pFileAvail->IsDataAvail(0, kReqSize)) { |
| 598 uint8_t buffer[1024]; | 576 uint8_t buffer[1024]; |
| (...skipping 160 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 759 std::unique_ptr<CPDF_Object> pHintStream( | 737 std::unique_ptr<CPDF_Object> pHintStream( |
| 760 ParseIndirectObjectAt(szHintStart, 0)); | 738 ParseIndirectObjectAt(szHintStart, 0)); |
| 761 CPDF_Stream* pStream = ToStream(pHintStream.get()); | 739 CPDF_Stream* pStream = ToStream(pHintStream.get()); |
| 762 if (pStream && pHintTables->LoadHintStream(pStream)) | 740 if (pStream && pHintTables->LoadHintStream(pStream)) |
| 763 m_pHintTables = std::move(pHintTables); | 741 m_pHintTables = std::move(pHintTables); |
| 764 | 742 |
| 765 m_docStatus = PDF_DATAAVAIL_DONE; | 743 m_docStatus = PDF_DATAAVAIL_DONE; |
| 766 return true; | 744 return true; |
| 767 } | 745 } |
| 768 | 746 |
| 769 CPDF_Object* CPDF_DataAvail::ParseIndirectObjectAt( | 747 std::unique_ptr<CPDF_Object> CPDF_DataAvail::ParseIndirectObjectAt( |
| 770 FX_FILESIZE pos, | 748 FX_FILESIZE pos, |
| 771 uint32_t objnum, | 749 uint32_t objnum, |
| 772 CPDF_IndirectObjectHolder* pObjList) { | 750 CPDF_IndirectObjectHolder* pObjList) { |
| 773 FX_FILESIZE SavedPos = m_syntaxParser.SavePos(); | 751 FX_FILESIZE SavedPos = m_syntaxParser.SavePos(); |
| 774 m_syntaxParser.RestorePos(pos); | 752 m_syntaxParser.RestorePos(pos); |
| 775 | 753 |
| 776 bool bIsNumber; | 754 bool bIsNumber; |
| 777 CFX_ByteString word = m_syntaxParser.GetNextWord(&bIsNumber); | 755 CFX_ByteString word = m_syntaxParser.GetNextWord(&bIsNumber); |
| 778 if (!bIsNumber) | 756 if (!bIsNumber) |
| 779 return nullptr; | 757 return nullptr; |
| 780 | 758 |
| 781 uint32_t parser_objnum = FXSYS_atoui(word.c_str()); | 759 uint32_t parser_objnum = FXSYS_atoui(word.c_str()); |
| 782 if (objnum && parser_objnum != objnum) | 760 if (objnum && parser_objnum != objnum) |
| 783 return nullptr; | 761 return nullptr; |
| 784 | 762 |
| 785 word = m_syntaxParser.GetNextWord(&bIsNumber); | 763 word = m_syntaxParser.GetNextWord(&bIsNumber); |
| 786 if (!bIsNumber) | 764 if (!bIsNumber) |
| 787 return nullptr; | 765 return nullptr; |
| 788 | 766 |
| 789 uint32_t gennum = FXSYS_atoui(word.c_str()); | 767 uint32_t gennum = FXSYS_atoui(word.c_str()); |
| 790 if (m_syntaxParser.GetKeyword() != "obj") { | 768 if (m_syntaxParser.GetKeyword() != "obj") { |
| 791 m_syntaxParser.RestorePos(SavedPos); | 769 m_syntaxParser.RestorePos(SavedPos); |
| 792 return nullptr; | 770 return nullptr; |
| 793 } | 771 } |
| 794 | 772 |
| 795 CPDF_Object* pObj = | 773 std::unique_ptr<CPDF_Object> pObj = |
| 796 m_syntaxParser.GetObject(pObjList, parser_objnum, gennum, true); | 774 m_syntaxParser.GetObject(pObjList, parser_objnum, gennum, true); |
| 797 m_syntaxParser.RestorePos(SavedPos); | 775 m_syntaxParser.RestorePos(SavedPos); |
| 798 return pObj; | 776 return pObj; |
| 799 } | 777 } |
| 800 | 778 |
| 801 CPDF_DataAvail::DocLinearizationStatus CPDF_DataAvail::IsLinearizedPDF() { | 779 CPDF_DataAvail::DocLinearizationStatus CPDF_DataAvail::IsLinearizedPDF() { |
| 802 const uint32_t kReqSize = 1024; | 780 const uint32_t kReqSize = 1024; |
| 803 if (!m_pFileAvail->IsDataAvail(0, kReqSize)) | 781 if (!m_pFileAvail->IsDataAvail(0, kReqSize)) |
| 804 return LinearizationUnknown; | 782 return LinearizationUnknown; |
| 805 | 783 |
| (...skipping 14 matching lines...) Expand all Loading... | |
| 820 | 798 |
| 821 bool CPDF_DataAvail::IsLinearized() { | 799 bool CPDF_DataAvail::IsLinearized() { |
| 822 return m_bLinearized; | 800 return m_bLinearized; |
| 823 } | 801 } |
| 824 | 802 |
| 825 bool CPDF_DataAvail::IsLinearizedFile(uint8_t* pData, uint32_t dwLen) { | 803 bool CPDF_DataAvail::IsLinearizedFile(uint8_t* pData, uint32_t dwLen) { |
| 826 if (m_pLinearized) | 804 if (m_pLinearized) |
| 827 return m_bLinearized; | 805 return m_bLinearized; |
| 828 | 806 |
| 829 ScopedFileStream file(FX_CreateMemoryStream(pData, (size_t)dwLen, false)); | 807 ScopedFileStream file(FX_CreateMemoryStream(pData, (size_t)dwLen, false)); |
| 830 | |
| 831 int32_t offset = GetHeaderOffset(file.get()); | 808 int32_t offset = GetHeaderOffset(file.get()); |
| 832 if (offset == -1) { | 809 if (offset == -1) { |
| 833 m_docStatus = PDF_DATAAVAIL_ERROR; | 810 m_docStatus = PDF_DATAAVAIL_ERROR; |
| 834 return false; | 811 return false; |
| 835 } | 812 } |
| 836 | 813 |
| 837 m_dwHeaderOffset = offset; | 814 m_dwHeaderOffset = offset; |
| 838 m_syntaxParser.InitParser(file.get(), offset); | 815 m_syntaxParser.InitParser(file.get(), offset); |
| 839 m_syntaxParser.RestorePos(m_syntaxParser.m_HeaderOffset + 9); | 816 m_syntaxParser.RestorePos(m_syntaxParser.m_HeaderOffset + 9); |
| 840 | 817 |
| (...skipping 84 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 925 | 902 |
| 926 ScopedFileStream file(FX_CreateMemoryStream(pBuf, (size_t)iSize, false)); | 903 ScopedFileStream file(FX_CreateMemoryStream(pBuf, (size_t)iSize, false)); |
| 927 m_parser.m_pSyntax->InitParser(file.get(), 0); | 904 m_parser.m_pSyntax->InitParser(file.get(), 0); |
| 928 | 905 |
| 929 bool bNumber; | 906 bool bNumber; |
| 930 CFX_ByteString objnum = m_parser.m_pSyntax->GetNextWord(&bNumber); | 907 CFX_ByteString objnum = m_parser.m_pSyntax->GetNextWord(&bNumber); |
| 931 if (!bNumber) | 908 if (!bNumber) |
| 932 return -1; | 909 return -1; |
| 933 | 910 |
| 934 uint32_t objNum = FXSYS_atoui(objnum.c_str()); | 911 uint32_t objNum = FXSYS_atoui(objnum.c_str()); |
| 935 CPDF_Object* pObj = m_parser.ParseIndirectObjectAt(nullptr, 0, objNum); | 912 std::unique_ptr<CPDF_Object> pObj = |
| 913 m_parser.ParseIndirectObjectAt(nullptr, 0, objNum); | |
| 914 | |
| 936 if (!pObj) { | 915 if (!pObj) { |
| 937 m_Pos += m_parser.m_pSyntax->SavePos(); | 916 m_Pos += m_parser.m_pSyntax->SavePos(); |
| 938 return 0; | 917 return 0; |
| 939 } | 918 } |
| 940 | 919 |
| 941 CPDF_Dictionary* pDict = pObj->GetDict(); | 920 CPDF_Dictionary* pDict = pObj->GetDict(); |
| 942 CPDF_Name* pName = ToName(pDict ? pDict->GetObjectFor("Type") : nullptr); | 921 CPDF_Name* pName = ToName(pDict ? pDict->GetObjectFor("Type") : nullptr); |
| 943 if (pName) { | 922 if (pName && pName->GetString() == "XRef") { |
| 944 if (pName->GetString() == "XRef") { | 923 m_Pos += m_parser.m_pSyntax->SavePos(); |
| 945 m_Pos += m_parser.m_pSyntax->SavePos(); | 924 xref_offset = pObj->GetDict()->GetIntegerFor("Prev"); |
| 946 xref_offset = pObj->GetDict()->GetIntegerFor("Prev"); | 925 return 1; |
| 947 delete pObj; | |
| 948 return 1; | |
| 949 } | |
| 950 } | 926 } |
| 951 delete pObj; | |
| 952 return -1; | 927 return -1; |
| 953 } | 928 } |
| 954 pHints->AddSegment(m_Pos, req_size); | 929 pHints->AddSegment(m_Pos, req_size); |
| 955 return 0; | 930 return 0; |
| 956 } | 931 } |
| 957 | 932 |
| 958 void CPDF_DataAvail::SetStartOffset(FX_FILESIZE dwOffset) { | 933 void CPDF_DataAvail::SetStartOffset(FX_FILESIZE dwOffset) { |
| 959 m_Pos = dwOffset; | 934 m_Pos = dwOffset; |
| 960 } | 935 } |
| 961 | 936 |
| (...skipping 274 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1236 m_docStatus = PDF_DATAAVAIL_PAGE; | 1211 m_docStatus = PDF_DATAAVAIL_PAGE; |
| 1237 return true; | 1212 return true; |
| 1238 } | 1213 } |
| 1239 } | 1214 } |
| 1240 } | 1215 } |
| 1241 | 1216 |
| 1242 bool CPDF_DataAvail::CheckArrayPageNode(uint32_t dwPageNo, | 1217 bool CPDF_DataAvail::CheckArrayPageNode(uint32_t dwPageNo, |
| 1243 PageNode* pPageNode, | 1218 PageNode* pPageNode, |
| 1244 DownloadHints* pHints) { | 1219 DownloadHints* pHints) { |
| 1245 bool bExist = false; | 1220 bool bExist = false; |
| 1246 CPDF_Object* pPages = GetObject(dwPageNo, pHints, &bExist); | 1221 std::unique_ptr<CPDF_Object> pPages = GetObject(dwPageNo, pHints, &bExist); |
| 1247 if (!bExist) { | 1222 if (!bExist) { |
| 1248 m_docStatus = PDF_DATAAVAIL_ERROR; | 1223 m_docStatus = PDF_DATAAVAIL_ERROR; |
| 1249 return false; | 1224 return false; |
| 1250 } | 1225 } |
| 1251 | 1226 |
| 1252 if (!pPages) { | 1227 if (!pPages) { |
| 1253 if (m_docStatus == PDF_DATAAVAIL_ERROR) { | 1228 if (m_docStatus == PDF_DATAAVAIL_ERROR) { |
| 1254 m_docStatus = PDF_DATAAVAIL_ERROR; | 1229 m_docStatus = PDF_DATAAVAIL_ERROR; |
| 1255 return false; | 1230 return false; |
| 1256 } | 1231 } |
| 1257 return false; | 1232 return false; |
| 1258 } | 1233 } |
| 1259 | 1234 |
| 1260 CPDF_Array* pArray = pPages->AsArray(); | 1235 CPDF_Array* pArray = pPages->AsArray(); |
| 1261 if (!pArray) { | 1236 if (!pArray) { |
| 1262 delete pPages; | |
| 1263 m_docStatus = PDF_DATAAVAIL_ERROR; | 1237 m_docStatus = PDF_DATAAVAIL_ERROR; |
| 1264 return false; | 1238 return false; |
| 1265 } | 1239 } |
| 1266 | 1240 |
| 1267 pPageNode->m_type = PDF_PAGENODE_PAGES; | 1241 pPageNode->m_type = PDF_PAGENODE_PAGES; |
| 1268 for (size_t i = 0; i < pArray->GetCount(); ++i) { | 1242 for (size_t i = 0; i < pArray->GetCount(); ++i) { |
| 1269 CPDF_Reference* pKid = ToReference(pArray->GetObjectAt(i)); | 1243 CPDF_Reference* pKid = ToReference(pArray->GetObjectAt(i)); |
| 1270 if (!pKid) | 1244 if (!pKid) |
| 1271 continue; | 1245 continue; |
| 1272 | 1246 |
| 1273 PageNode* pNode = new PageNode(); | 1247 PageNode* pNode = new PageNode(); |
| 1274 pPageNode->m_childNode.Add(pNode); | 1248 pPageNode->m_childNode.Add(pNode); |
| 1275 pNode->m_dwPageNo = pKid->GetRefObjNum(); | 1249 pNode->m_dwPageNo = pKid->GetRefObjNum(); |
| 1276 } | 1250 } |
| 1277 delete pPages; | |
| 1278 return true; | 1251 return true; |
| 1279 } | 1252 } |
| 1280 | 1253 |
| 1281 bool CPDF_DataAvail::CheckUnkownPageNode(uint32_t dwPageNo, | 1254 bool CPDF_DataAvail::CheckUnkownPageNode(uint32_t dwPageNo, |
| 1282 PageNode* pPageNode, | 1255 PageNode* pPageNode, |
| 1283 DownloadHints* pHints) { | 1256 DownloadHints* pHints) { |
| 1284 bool bExist = false; | 1257 bool bExist = false; |
| 1285 CPDF_Object* pPage = GetObject(dwPageNo, pHints, &bExist); | 1258 std::unique_ptr<CPDF_Object> pPage = GetObject(dwPageNo, pHints, &bExist); |
| 1286 if (!bExist) { | 1259 if (!bExist) { |
| 1287 m_docStatus = PDF_DATAAVAIL_ERROR; | 1260 m_docStatus = PDF_DATAAVAIL_ERROR; |
| 1288 return false; | 1261 return false; |
| 1289 } | 1262 } |
| 1290 | 1263 |
| 1291 if (!pPage) { | 1264 if (!pPage) { |
| 1292 if (m_docStatus == PDF_DATAAVAIL_ERROR) | 1265 if (m_docStatus == PDF_DATAAVAIL_ERROR) |
| 1293 m_docStatus = PDF_DATAAVAIL_ERROR; | 1266 m_docStatus = PDF_DATAAVAIL_ERROR; |
| 1294 return false; | 1267 return false; |
| 1295 } | 1268 } |
| 1296 | 1269 |
| 1297 if (pPage->IsArray()) { | 1270 if (pPage->IsArray()) { |
| 1298 pPageNode->m_dwPageNo = dwPageNo; | 1271 pPageNode->m_dwPageNo = dwPageNo; |
| 1299 pPageNode->m_type = PDF_PAGENODE_ARRAY; | 1272 pPageNode->m_type = PDF_PAGENODE_ARRAY; |
| 1300 delete pPage; | |
| 1301 return true; | 1273 return true; |
| 1302 } | 1274 } |
| 1303 | 1275 |
| 1304 if (!pPage->IsDictionary()) { | 1276 if (!pPage->IsDictionary()) { |
| 1305 delete pPage; | |
| 1306 m_docStatus = PDF_DATAAVAIL_ERROR; | 1277 m_docStatus = PDF_DATAAVAIL_ERROR; |
| 1307 return false; | 1278 return false; |
| 1308 } | 1279 } |
| 1309 | 1280 |
| 1310 pPageNode->m_dwPageNo = dwPageNo; | 1281 pPageNode->m_dwPageNo = dwPageNo; |
| 1311 CPDF_Dictionary* pDict = pPage->GetDict(); | 1282 CPDF_Dictionary* pDict = pPage->GetDict(); |
| 1312 CFX_ByteString type = pDict->GetStringFor("Type"); | 1283 CFX_ByteString type = pDict->GetStringFor("Type"); |
| 1313 if (type == "Pages") { | 1284 if (type == "Pages") { |
| 1314 pPageNode->m_type = PDF_PAGENODE_PAGES; | 1285 pPageNode->m_type = PDF_PAGENODE_PAGES; |
| 1315 CPDF_Object* pKids = pDict->GetObjectFor("Kids"); | 1286 CPDF_Object* pKids = pDict->GetObjectFor("Kids"); |
| (...skipping 20 matching lines...) Expand all Loading... | |
| 1336 pPageNode->m_childNode.Add(pNode); | 1307 pPageNode->m_childNode.Add(pNode); |
| 1337 pNode->m_dwPageNo = pKid->GetRefObjNum(); | 1308 pNode->m_dwPageNo = pKid->GetRefObjNum(); |
| 1338 } | 1309 } |
| 1339 } break; | 1310 } break; |
| 1340 default: | 1311 default: |
| 1341 break; | 1312 break; |
| 1342 } | 1313 } |
| 1343 } else if (type == "Page") { | 1314 } else if (type == "Page") { |
| 1344 pPageNode->m_type = PDF_PAGENODE_PAGE; | 1315 pPageNode->m_type = PDF_PAGENODE_PAGE; |
| 1345 } else { | 1316 } else { |
| 1346 delete pPage; | |
| 1347 m_docStatus = PDF_DATAAVAIL_ERROR; | 1317 m_docStatus = PDF_DATAAVAIL_ERROR; |
| 1348 return false; | 1318 return false; |
| 1349 } | 1319 } |
| 1350 delete pPage; | |
| 1351 return true; | 1320 return true; |
| 1352 } | 1321 } |
| 1353 | 1322 |
| 1354 bool CPDF_DataAvail::CheckPageNode(CPDF_DataAvail::PageNode& pageNodes, | 1323 bool CPDF_DataAvail::CheckPageNode(CPDF_DataAvail::PageNode& pageNodes, |
| 1355 int32_t iPage, | 1324 int32_t iPage, |
| 1356 int32_t& iCount, | 1325 int32_t& iCount, |
| 1357 DownloadHints* pHints, | 1326 DownloadHints* pHints, |
| 1358 int level) { | 1327 int level) { |
| 1359 if (level >= kMaxPageRecursionDepth) | 1328 if (level >= kMaxPageRecursionDepth) |
| 1360 return false; | 1329 return false; |
| (...skipping 56 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1417 } | 1386 } |
| 1418 m_docStatus = PDF_DATAAVAIL_ERROR; | 1387 m_docStatus = PDF_DATAAVAIL_ERROR; |
| 1419 return true; | 1388 return true; |
| 1420 } | 1389 } |
| 1421 int32_t iCount = -1; | 1390 int32_t iCount = -1; |
| 1422 return CheckPageNode(m_pageNodes, iPage, iCount, pHints, 0); | 1391 return CheckPageNode(m_pageNodes, iPage, iCount, pHints, 0); |
| 1423 } | 1392 } |
| 1424 | 1393 |
| 1425 bool CPDF_DataAvail::CheckPageCount(DownloadHints* pHints) { | 1394 bool CPDF_DataAvail::CheckPageCount(DownloadHints* pHints) { |
| 1426 bool bExist = false; | 1395 bool bExist = false; |
| 1427 CPDF_Object* pPages = GetObject(m_PagesObjNum, pHints, &bExist); | 1396 std::unique_ptr<CPDF_Object> pPages = |
| 1397 GetObject(m_PagesObjNum, pHints, &bExist); | |
| 1428 if (!bExist) { | 1398 if (!bExist) { |
| 1429 m_docStatus = PDF_DATAAVAIL_ERROR; | 1399 m_docStatus = PDF_DATAAVAIL_ERROR; |
| 1430 return false; | 1400 return false; |
| 1431 } | 1401 } |
| 1432 | 1402 |
| 1433 if (!pPages) | 1403 if (!pPages) |
|
Tom Sepez
2016/11/07 18:58:44
note: probably can re-order this test and nest the
| |
| 1434 return false; | 1404 return false; |
| 1435 | 1405 |
| 1436 CPDF_Dictionary* pPagesDict = pPages->GetDict(); | 1406 CPDF_Dictionary* pPagesDict = pPages->GetDict(); |
| 1437 if (!pPagesDict) { | 1407 if (!pPagesDict) { |
| 1438 delete pPages; | |
| 1439 m_docStatus = PDF_DATAAVAIL_ERROR; | 1408 m_docStatus = PDF_DATAAVAIL_ERROR; |
| 1440 return false; | 1409 return false; |
| 1441 } | 1410 } |
| 1442 | 1411 |
| 1443 if (!pPagesDict->KeyExist("Kids")) { | 1412 if (!pPagesDict->KeyExist("Kids")) |
| 1444 delete pPages; | |
| 1445 return true; | 1413 return true; |
| 1446 } | |
| 1447 | 1414 |
| 1448 int count = pPagesDict->GetIntegerFor("Count"); | 1415 return pPagesDict->GetIntegerFor("Count") > 0; |
| 1449 if (count > 0) { | |
| 1450 delete pPages; | |
| 1451 return true; | |
| 1452 } | |
| 1453 | |
| 1454 delete pPages; | |
| 1455 return false; | |
| 1456 } | 1416 } |
| 1457 | 1417 |
| 1458 bool CPDF_DataAvail::LoadDocPages(DownloadHints* pHints) { | 1418 bool CPDF_DataAvail::LoadDocPages(DownloadHints* pHints) { |
| 1459 if (!CheckUnkownPageNode(m_PagesObjNum, &m_pageNodes, pHints)) | 1419 if (!CheckUnkownPageNode(m_PagesObjNum, &m_pageNodes, pHints)) |
| 1460 return false; | 1420 return false; |
| 1461 | 1421 |
| 1462 if (CheckPageCount(pHints)) { | 1422 if (CheckPageCount(pHints)) { |
| 1463 m_docStatus = PDF_DATAAVAIL_PAGE; | 1423 m_docStatus = PDF_DATAAVAIL_PAGE; |
| 1464 return true; | 1424 return true; |
| 1465 } | 1425 } |
| (...skipping 291 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1757 FX_FILESIZE szPageLength = 0; | 1717 FX_FILESIZE szPageLength = 0; |
| 1758 uint32_t dwObjNum = 0; | 1718 uint32_t dwObjNum = 0; |
| 1759 const bool bPagePosGot = m_pHintTables->GetPagePos(index, &szPageStartPos, | 1719 const bool bPagePosGot = m_pHintTables->GetPagePos(index, &szPageStartPos, |
| 1760 &szPageLength, &dwObjNum); | 1720 &szPageLength, &dwObjNum); |
| 1761 if (!bPagePosGot || !dwObjNum) | 1721 if (!bPagePosGot || !dwObjNum) |
| 1762 return nullptr; | 1722 return nullptr; |
| 1763 // We should say to the document, which object is the page. | 1723 // We should say to the document, which object is the page. |
| 1764 m_pDocument->SetPageObjNum(index, dwObjNum); | 1724 m_pDocument->SetPageObjNum(index, dwObjNum); |
| 1765 // Page object already can be parsed in document. | 1725 // Page object already can be parsed in document. |
| 1766 if (!m_pDocument->GetIndirectObject(dwObjNum)) { | 1726 if (!m_pDocument->GetIndirectObject(dwObjNum)) { |
| 1767 m_syntaxParser.InitParser(m_pFileRead, (uint32_t)szPageStartPos); | 1727 m_syntaxParser.InitParser( |
| 1728 m_pFileRead, pdfium::base::checked_cast<uint32_t>(szPageStartPos)); | |
| 1768 m_pDocument->ReplaceIndirectObjectIfHigherGeneration( | 1729 m_pDocument->ReplaceIndirectObjectIfHigherGeneration( |
| 1769 dwObjNum, pdfium::WrapUnique<CPDF_Object>( | 1730 dwObjNum, ParseIndirectObjectAt(0, dwObjNum, m_pDocument)); |
| 1770 ParseIndirectObjectAt(0, dwObjNum, m_pDocument))); | |
| 1771 } | 1731 } |
| 1772 return m_pDocument->GetPage(index); | 1732 return m_pDocument->GetPage(index); |
| 1773 } | 1733 } |
| 1774 | 1734 |
| 1775 CPDF_DataAvail::DocFormStatus CPDF_DataAvail::IsFormAvail( | 1735 CPDF_DataAvail::DocFormStatus CPDF_DataAvail::IsFormAvail( |
| 1776 DownloadHints* pHints) { | 1736 DownloadHints* pHints) { |
| 1777 if (!m_pDocument) | 1737 if (!m_pDocument) |
| 1778 return FormAvailable; | 1738 return FormAvailable; |
| 1779 | 1739 |
| 1780 if (!m_bLinearizedFormParamLoad) { | 1740 if (!m_bLinearizedFormParamLoad) { |
| (...skipping 26 matching lines...) Expand all Loading... | |
| 1807 return FormAvailable; | 1767 return FormAvailable; |
| 1808 } | 1768 } |
| 1809 | 1769 |
| 1810 CPDF_DataAvail::PageNode::PageNode() : m_type(PDF_PAGENODE_UNKNOWN) {} | 1770 CPDF_DataAvail::PageNode::PageNode() : m_type(PDF_PAGENODE_UNKNOWN) {} |
| 1811 | 1771 |
| 1812 CPDF_DataAvail::PageNode::~PageNode() { | 1772 CPDF_DataAvail::PageNode::~PageNode() { |
| 1813 for (int32_t i = 0; i < m_childNode.GetSize(); ++i) | 1773 for (int32_t i = 0; i < m_childNode.GetSize(); ++i) |
| 1814 delete m_childNode[i]; | 1774 delete m_childNode[i]; |
| 1815 m_childNode.RemoveAll(); | 1775 m_childNode.RemoveAll(); |
| 1816 } | 1776 } |
| OLD | NEW |