1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
|
// Copyright 2016 PDFium Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
#include "core/fxcrt/include/cfx_count_ref.h"
#include <map>
#include <string>
#include "testing/fx_string_testhelpers.h"
#include "testing/gtest/include/gtest/gtest.h"
namespace {
class Observer {
public:
void OnConstruct(const std::string& name) { construction_counts_[name]++; }
void OnDestruct(const std::string& name) { destruction_counts_[name]++; }
int GetConstructionCount(const std::string& name) {
return construction_counts_[name];
}
int GetDestructionCount(const std::string& name) {
return destruction_counts_[name];
}
private:
std::map<std::string, int> construction_counts_;
std::map<std::string, int> destruction_counts_;
};
class Object {
public:
Object(Observer* observer, const std::string& name)
: name_(name), observer_(observer) {
observer->OnConstruct(name_);
}
Object(const Object& that) : name_(that.name_), observer_(that.observer_) {
observer_->OnConstruct(name_);
}
~Object() { observer_->OnDestruct(name_); }
private:
std::string name_;
Observer* observer_;
};
} // namespace
TEST(fxcrt, CountRefNull) {
Observer observer;
{
CFX_CountRef<Object> ptr;
EXPECT_EQ(nullptr, ptr.GetObject());
}
}
TEST(fxcrt, CountRefCopy) {
Observer observer;
{
CFX_CountRef<Object> ptr1;
ptr1.Emplace(&observer, std::string("one"));
{
CFX_CountRef<Object> ptr2 = ptr1;
EXPECT_EQ(1, observer.GetConstructionCount("one"));
EXPECT_EQ(0, observer.GetDestructionCount("one"));
}
{
CFX_CountRef<Object> ptr3(ptr1);
EXPECT_EQ(1, observer.GetConstructionCount("one"));
EXPECT_EQ(0, observer.GetDestructionCount("one"));
}
EXPECT_EQ(1, observer.GetConstructionCount("one"));
EXPECT_EQ(0, observer.GetDestructionCount("one"));
}
EXPECT_EQ(1, observer.GetDestructionCount("one"));
}
TEST(fxcrt, CountRefAssignOverOld) {
Observer observer;
{
CFX_CountRef<Object> ptr1;
ptr1.Emplace(&observer, std::string("one"));
ptr1.Emplace(&observer, std::string("two"));
EXPECT_EQ(1, observer.GetConstructionCount("one"));
EXPECT_EQ(1, observer.GetConstructionCount("two"));
EXPECT_EQ(1, observer.GetDestructionCount("one"));
EXPECT_EQ(0, observer.GetDestructionCount("two"));
}
EXPECT_EQ(1, observer.GetDestructionCount("two"));
}
TEST(fxcrt, CountRefAssignOverRetained) {
Observer observer;
{
CFX_CountRef<Object> ptr1;
ptr1.Emplace(&observer, std::string("one"));
CFX_CountRef<Object> ptr2(ptr1);
ptr1.Emplace(&observer, std::string("two"));
EXPECT_EQ(1, observer.GetConstructionCount("one"));
EXPECT_EQ(1, observer.GetConstructionCount("two"));
EXPECT_EQ(0, observer.GetDestructionCount("one"));
EXPECT_EQ(0, observer.GetDestructionCount("two"));
}
EXPECT_EQ(1, observer.GetDestructionCount("one"));
EXPECT_EQ(1, observer.GetDestructionCount("two"));
}
TEST(fxcrt, CountRefGetModify) {
Observer observer;
{
CFX_CountRef<Object> ptr;
EXPECT_NE(nullptr, ptr.GetPrivateCopy(&observer, std::string("one")));
EXPECT_EQ(1, observer.GetConstructionCount("one"));
EXPECT_EQ(0, observer.GetDestructionCount("one"));
EXPECT_NE(nullptr, ptr.GetPrivateCopy(&observer, std::string("one")));
EXPECT_EQ(1, observer.GetConstructionCount("one"));
EXPECT_EQ(0, observer.GetDestructionCount("one"));
{
CFX_CountRef<Object> other(ptr);
EXPECT_NE(nullptr, ptr.GetPrivateCopy(&observer, std::string("one")));
EXPECT_EQ(2, observer.GetConstructionCount("one"));
EXPECT_EQ(0, observer.GetDestructionCount("one"));
}
EXPECT_EQ(2, observer.GetConstructionCount("one"));
EXPECT_EQ(1, observer.GetDestructionCount("one"));
}
EXPECT_EQ(2, observer.GetDestructionCount("one"));
}
|