• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright 2017 PDFium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4 
5 #include "core/fpdfapi/parser/cpdf_indirect_object_holder.h"
6 
7 #include <memory>
8 #include <utility>
9 
10 #include "core/fpdfapi/parser/cpdf_null.h"
11 #include "testing/gmock/include/gmock/gmock.h"
12 #include "testing/gtest/include/gtest/gtest.h"
13 #include "third_party/base/ptr_util.h"
14 
15 namespace {
16 
17 class MockIndirectObjectHolder final : public CPDF_IndirectObjectHolder {
18  public:
MockIndirectObjectHolder()19   MockIndirectObjectHolder() {}
~MockIndirectObjectHolder()20   ~MockIndirectObjectHolder() override {}
21 
22   MOCK_METHOD1(ParseIndirectObject, RetainPtr<CPDF_Object>(uint32_t objnum));
23 };
24 
25 }  // namespace
26 
TEST(CPDF_IndirectObjectHolderTest,RecursiveParseOfSameObject)27 TEST(CPDF_IndirectObjectHolderTest, RecursiveParseOfSameObject) {
28   MockIndirectObjectHolder mock_holder;
29   // ParseIndirectObject should not be called again on recursively same object
30   // parse request.
31   EXPECT_CALL(mock_holder, ParseIndirectObject(::testing::_))
32       .WillOnce(::testing::WithArg<0>(::testing::Invoke(
33           [&mock_holder](uint32_t objnum) -> RetainPtr<CPDF_Object> {
34             const CPDF_Object* same_parse =
35                 mock_holder.GetOrParseIndirectObject(objnum);
36             CHECK(!same_parse);
37             return pdfium::MakeRetain<CPDF_Null>();
38           })));
39 
40   EXPECT_TRUE(mock_holder.GetOrParseIndirectObject(1000));
41 }
42 
TEST(CPDF_IndirectObjectHolderTest,GetObjectMethods)43 TEST(CPDF_IndirectObjectHolderTest, GetObjectMethods) {
44   static constexpr uint32_t kObjNum = 1000;
45   MockIndirectObjectHolder mock_holder;
46 
47   EXPECT_CALL(mock_holder, ParseIndirectObject(::testing::_)).Times(0);
48   EXPECT_FALSE(mock_holder.GetIndirectObject(kObjNum));
49   ::testing::Mock::VerifyAndClearExpectations(&mock_holder);
50 
51   EXPECT_CALL(mock_holder, ParseIndirectObject(::testing::_))
52       .WillOnce(::testing::WithArg<0>(
53           ::testing::Invoke([](uint32_t objnum) -> RetainPtr<CPDF_Object> {
54             return pdfium::MakeRetain<CPDF_Null>();
55           })));
56   EXPECT_TRUE(mock_holder.GetOrParseIndirectObject(kObjNum));
57   ::testing::Mock::VerifyAndClearExpectations(&mock_holder);
58 
59   EXPECT_CALL(mock_holder, ParseIndirectObject(::testing::_)).Times(0);
60   ASSERT_TRUE(mock_holder.GetIndirectObject(kObjNum));
61   ::testing::Mock::VerifyAndClearExpectations(&mock_holder);
62 
63   EXPECT_EQ(kObjNum, mock_holder.GetIndirectObject(kObjNum)->GetObjNum());
64 }
65 
TEST(CPDF_IndirectObjectHolderTest,ParseInvalidObjNum)66 TEST(CPDF_IndirectObjectHolderTest, ParseInvalidObjNum) {
67   MockIndirectObjectHolder mock_holder;
68 
69   EXPECT_CALL(mock_holder, ParseIndirectObject(::testing::_)).Times(0);
70   EXPECT_FALSE(
71       mock_holder.GetOrParseIndirectObject(CPDF_Object::kInvalidObjNum));
72 }
73 
TEST(CPDF_IndirectObjectHolderTest,ReplaceObjectWithInvalidObjNum)74 TEST(CPDF_IndirectObjectHolderTest, ReplaceObjectWithInvalidObjNum) {
75   MockIndirectObjectHolder mock_holder;
76 
77   EXPECT_CALL(mock_holder, ParseIndirectObject(::testing::_)).Times(0);
78   EXPECT_FALSE(mock_holder.ReplaceIndirectObjectIfHigherGeneration(
79       CPDF_Object::kInvalidObjNum, pdfium::MakeRetain<CPDF_Null>()));
80 }
81