OLD | NEW |
1 /* | 1 /* |
2 * Copyright 2013 Google Inc. | 2 * Copyright 2013 Google Inc. |
3 * | 3 * |
4 * Use of this source code is governed by a BSD-style license that can be | 4 * Use of this source code is governed by a BSD-style license that can be |
5 * found in the LICENSE file. | 5 * found in the LICENSE file. |
6 */ | 6 */ |
7 | 7 |
8 #if SK_SUPPORT_GPU | 8 #if SK_SUPPORT_GPU |
9 | 9 |
10 #include "GrContext.h" | 10 #include "GrContext.h" |
11 #include "GrContextFactory.h" | 11 #include "GrContextFactory.h" |
12 #include "GrGpu.h" | 12 #include "GrGpu.h" |
| 13 #include "GrResourceCache.h" |
13 #include "GrResourceCache2.h" | 14 #include "GrResourceCache2.h" |
14 #include "SkCanvas.h" | 15 #include "SkCanvas.h" |
15 #include "SkGr.h" | |
16 #include "SkMessageBus.h" | |
17 #include "SkSurface.h" | 16 #include "SkSurface.h" |
18 #include "Test.h" | 17 #include "Test.h" |
19 | 18 |
20 static const int gWidth = 640; | 19 static const int gWidth = 640; |
21 static const int gHeight = 480; | 20 static const int gHeight = 480; |
22 | 21 |
23 //////////////////////////////////////////////////////////////////////////////// | 22 //////////////////////////////////////////////////////////////////////////////// |
24 static void test_cache(skiatest::Reporter* reporter, GrContext* context, SkCanva
s* canvas) { | 23 static void test_cache(skiatest::Reporter* reporter, GrContext* context, SkCanva
s* canvas) { |
25 const SkIRect size = SkIRect::MakeWH(gWidth, gHeight); | 24 const SkIRect size = SkIRect::MakeWH(gWidth, gHeight); |
26 | 25 |
(...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
61 context->setResourceCacheLimits(oldMaxNum, oldMaxBytes); | 60 context->setResourceCacheLimits(oldMaxNum, oldMaxBytes); |
62 } | 61 } |
63 | 62 |
64 class TestResource : public GrGpuResource { | 63 class TestResource : public GrGpuResource { |
65 static const size_t kDefaultSize = 100; | 64 static const size_t kDefaultSize = 100; |
66 | 65 |
67 public: | 66 public: |
68 SK_DECLARE_INST_COUNT(TestResource); | 67 SK_DECLARE_INST_COUNT(TestResource); |
69 TestResource(GrGpu* gpu) | 68 TestResource(GrGpu* gpu) |
70 : INHERITED(gpu, false) | 69 : INHERITED(gpu, false) |
| 70 , fCache(NULL) |
71 , fToDelete(NULL) | 71 , fToDelete(NULL) |
72 , fSize(kDefaultSize) { | 72 , fSize(kDefaultSize) { |
73 ++fNumAlive; | 73 ++fNumAlive; |
74 this->registerWithCache(); | 74 this->registerWithCache(); |
75 } | 75 } |
76 | 76 |
77 TestResource(GrGpu* gpu, const GrResourceKey& scratchKey) | 77 TestResource(GrGpu* gpu, const GrResourceKey& scratchKey) |
78 : INHERITED(gpu, false) | 78 : INHERITED(gpu, false) |
| 79 , fCache(NULL) |
79 , fToDelete(NULL) | 80 , fToDelete(NULL) |
80 , fSize(kDefaultSize) { | 81 , fSize(kDefaultSize) { |
81 this->setScratchKey(scratchKey); | 82 this->setScratchKey(scratchKey); |
82 ++fNumAlive; | 83 ++fNumAlive; |
83 this->registerWithCache(); | 84 this->registerWithCache(); |
84 } | 85 } |
85 | 86 |
86 ~TestResource() { | 87 ~TestResource() { |
87 --fNumAlive; | 88 --fNumAlive; |
88 SkSafeUnref(fToDelete); | 89 if (fToDelete) { |
| 90 // Breaks our little 2-element cycle below. |
| 91 fToDelete->setDeleteWhenDestroyed(NULL, NULL); |
| 92 fCache->deleteResource(fToDelete->cacheAccess().getCacheEntry()); |
| 93 } |
89 this->release(); | 94 this->release(); |
90 } | 95 } |
91 | 96 |
92 void setSize(size_t size) { | 97 void setSize(size_t size) { |
93 fSize = size; | 98 fSize = size; |
94 this->didChangeGpuMemorySize(); | 99 this->didChangeGpuMemorySize(); |
95 } | 100 } |
96 | 101 |
97 static int NumAlive() { return fNumAlive; } | 102 static int NumAlive() { return fNumAlive; } |
98 | 103 |
99 void setUnrefWhenDestroyed(TestResource* resource) { | 104 void setDeleteWhenDestroyed(GrResourceCache* cache, TestResource* resource)
{ |
100 SkRefCnt_SafeAssign(fToDelete, resource); | 105 fCache = cache; |
| 106 fToDelete = resource; |
101 } | 107 } |
102 | 108 |
103 private: | 109 private: |
104 size_t onGpuMemorySize() const SK_OVERRIDE { return fSize; } | 110 size_t onGpuMemorySize() const SK_OVERRIDE { return fSize; } |
105 | 111 |
| 112 GrResourceCache* fCache; |
106 TestResource* fToDelete; | 113 TestResource* fToDelete; |
107 size_t fSize; | 114 size_t fSize; |
108 static int fNumAlive; | 115 static int fNumAlive; |
109 | 116 |
110 typedef GrGpuResource INHERITED; | 117 typedef GrGpuResource INHERITED; |
111 }; | 118 }; |
112 int TestResource::fNumAlive = 0; | 119 int TestResource::fNumAlive = 0; |
113 | 120 |
114 static void test_no_key(skiatest::Reporter* reporter) { | |
115 SkAutoTUnref<GrContext> context(GrContext::CreateMockContext()); | |
116 REPORTER_ASSERT(reporter, SkToBool(context)); | |
117 if (NULL == context) { | |
118 return; | |
119 } | |
120 context->setResourceCacheLimits(10, 30000); | |
121 GrResourceCache2* cache2 = context->getResourceCache2(); | |
122 cache2->purgeAllUnlocked(); | |
123 SkASSERT(0 == cache2->getResourceCount() && 0 == cache2->getResourceBytes())
; | |
124 | |
125 // Create a bunch of resources with no keys | |
126 TestResource* a = new TestResource(context->getGpu()); | |
127 TestResource* b = new TestResource(context->getGpu()); | |
128 TestResource* c = new TestResource(context->getGpu()); | |
129 TestResource* d = new TestResource(context->getGpu()); | |
130 a->setSize(11); | |
131 b->setSize(12); | |
132 c->setSize(13); | |
133 d->setSize(14); | |
134 | |
135 REPORTER_ASSERT(reporter, 4 == TestResource::NumAlive()); | |
136 REPORTER_ASSERT(reporter, 4 == cache2->getResourceCount()); | |
137 REPORTER_ASSERT(reporter, a->gpuMemorySize() + b->gpuMemorySize() + c->gpuMe
morySize() + | |
138 d->gpuMemorySize() == cache2->getResourceBytes()); | |
139 | |
140 // Should be safe to purge without deleting the resources since we still hav
e refs. | |
141 cache2->purgeAllUnlocked(); | |
142 REPORTER_ASSERT(reporter, 4 == TestResource::NumAlive()); | |
143 | |
144 // Since the resources have neither content nor scratch keys, delete immedia
tely upon unref. | |
145 | |
146 a->unref(); | |
147 REPORTER_ASSERT(reporter, 3 == TestResource::NumAlive()); | |
148 REPORTER_ASSERT(reporter, 3 == cache2->getResourceCount()); | |
149 REPORTER_ASSERT(reporter, b->gpuMemorySize() + c->gpuMemorySize() + d->gpuMe
morySize() == | |
150 cache2->getResourceBytes()); | |
151 | |
152 c->unref(); | |
153 REPORTER_ASSERT(reporter, 2 == TestResource::NumAlive()); | |
154 REPORTER_ASSERT(reporter, 2 == cache2->getResourceCount()); | |
155 REPORTER_ASSERT(reporter, b->gpuMemorySize() + d->gpuMemorySize() == | |
156 cache2->getResourceBytes()); | |
157 | |
158 d->unref(); | |
159 REPORTER_ASSERT(reporter, 1 == TestResource::NumAlive()); | |
160 REPORTER_ASSERT(reporter, 1 == cache2->getResourceCount()); | |
161 REPORTER_ASSERT(reporter, b->gpuMemorySize() == cache2->getResourceBytes()); | |
162 | |
163 b->unref(); | |
164 REPORTER_ASSERT(reporter, 0 == TestResource::NumAlive()); | |
165 REPORTER_ASSERT(reporter, 0 == cache2->getResourceCount()); | |
166 REPORTER_ASSERT(reporter, 0 == cache2->getResourceBytes()); | |
167 } | |
168 | |
169 static void test_duplicate_scratch_key(skiatest::Reporter* reporter) { | 121 static void test_duplicate_scratch_key(skiatest::Reporter* reporter) { |
170 SkAutoTUnref<GrContext> context(GrContext::CreateMockContext()); | 122 SkAutoTUnref<GrContext> context(GrContext::CreateMockContext()); |
171 REPORTER_ASSERT(reporter, SkToBool(context)); | 123 REPORTER_ASSERT(reporter, SkToBool(context)); |
172 if (NULL == context) { | 124 if (NULL == context) { |
173 return; | 125 return; |
174 } | 126 } |
175 context->setResourceCacheLimits(5, 30000); | 127 context->setResourceCacheLimits(5, 30000); |
176 GrResourceCache2* cache2 = context->getResourceCache2(); | 128 GrResourceCache* cache = context->getResourceCache(); |
177 cache2->purgeAllUnlocked(); | 129 SkDEBUGCODE(GrResourceCache2* cache2 = context->getResourceCache2();) |
178 SkASSERT(0 == cache2->getResourceCount() && 0 == cache2->getResourceBytes())
; | 130 cache->purgeAllUnlocked(); |
| 131 SkASSERT(0 == cache->getCachedResourceCount() && 0 == cache->getCachedResour
ceBytes()); |
179 | 132 |
180 GrCacheID::Key keyData; | 133 GrCacheID::Key keyData; |
181 memset(&keyData, 0, sizeof(keyData)); | 134 memset(&keyData, 0, sizeof(keyData)); |
182 GrCacheID::Domain domain = GrResourceKey::ScratchDomain(); | 135 GrCacheID::Domain domain = GrResourceKey::ScratchDomain(); |
183 GrResourceKey::ResourceType t = GrResourceKey::GenerateResourceType(); | 136 GrResourceKey::ResourceType t = GrResourceKey::GenerateResourceType(); |
184 GrResourceKey scratchKey(GrCacheID(domain, keyData), t, 0); | 137 GrResourceKey scratchKey(GrCacheID(domain, keyData), t, 0); |
185 | 138 |
186 // Create two resources that have the same scratch key. | 139 // Create two resources that have the same scratch key. |
187 TestResource* a = new TestResource(context->getGpu(), scratchKey); | 140 TestResource* a = new TestResource(context->getGpu(), scratchKey); |
188 TestResource* b = new TestResource(context->getGpu(), scratchKey); | 141 TestResource* b = new TestResource(context->getGpu(), scratchKey); |
189 a->setSize(11); | 142 a->setSize(11); |
190 b->setSize(12); | 143 b->setSize(12); |
191 // Scratch resources are registered with GrResourceCache2 just by existing.
There are 2. | 144 // Scratch resources are registered with GrResourceCache2 just by existing.
There are 2. |
| 145 SkDEBUGCODE(REPORTER_ASSERT(reporter, 2 == cache2->countScratchEntriesForKey
(scratchKey));) |
| 146 |
| 147 REPORTER_ASSERT(reporter, cache->addResource(scratchKey, a)); |
| 148 |
| 149 SkDEBUGCODE(REPORTER_ASSERT(reporter, 2 == cache2->countScratchEntriesForKey
(scratchKey));) |
| 150 |
| 151 // Can't add the same resource twice. |
| 152 REPORTER_ASSERT(reporter, !cache->addResource(scratchKey, a)); |
| 153 REPORTER_ASSERT(reporter, 1 == cache->getCachedResourceCount()); |
| 154 REPORTER_ASSERT(reporter, a->gpuMemorySize() == cache->getCachedResourceByte
s()); |
| 155 SkDEBUGCODE(REPORTER_ASSERT(reporter, 2 == cache2->countScratchEntriesForKey
(scratchKey));) |
| 156 |
| 157 // Add a second with the same key. |
| 158 REPORTER_ASSERT(reporter, cache->addResource(scratchKey, b)); |
| 159 REPORTER_ASSERT(reporter, 2 == cache->getCachedResourceCount()); |
| 160 REPORTER_ASSERT(reporter, a->gpuMemorySize() + b->gpuMemorySize() == |
| 161 cache->getCachedResourceBytes()); |
192 REPORTER_ASSERT(reporter, 2 == TestResource::NumAlive()); | 162 REPORTER_ASSERT(reporter, 2 == TestResource::NumAlive()); |
193 SkDEBUGCODE(REPORTER_ASSERT(reporter, 2 == cache2->countScratchEntriesForKey
(scratchKey));) | 163 SkDEBUGCODE(REPORTER_ASSERT(reporter, 2 == cache2->countScratchEntriesForKey
(scratchKey));) |
194 REPORTER_ASSERT(reporter, 2 == cache2->getResourceCount()); | |
195 REPORTER_ASSERT(reporter, a->gpuMemorySize() + b->gpuMemorySize() == | |
196 cache2->getResourceBytes()); | |
197 | 164 |
198 // Our refs mean that the resources are non purgable. | 165 // Our refs mean that the resources are non purgable. |
199 cache2->purgeAllUnlocked(); | 166 cache->purgeAllUnlocked(); |
200 REPORTER_ASSERT(reporter, 2 == TestResource::NumAlive()); | 167 REPORTER_ASSERT(reporter, 2 == TestResource::NumAlive()); |
201 REPORTER_ASSERT(reporter, 2 == cache2->getResourceCount()); | 168 REPORTER_ASSERT(reporter, 2 == cache->getCachedResourceCount()); |
202 | 169 |
203 // Unref but don't purge | 170 // Unref but don't purge |
204 a->unref(); | 171 a->unref(); |
205 b->unref(); | 172 b->unref(); |
206 REPORTER_ASSERT(reporter, 2 == TestResource::NumAlive()); | 173 REPORTER_ASSERT(reporter, 2 == TestResource::NumAlive()); |
207 SkDEBUGCODE(REPORTER_ASSERT(reporter, 2 == cache2->countScratchEntriesForKey
(scratchKey));) | 174 SkDEBUGCODE(REPORTER_ASSERT(reporter, 2 == cache2->countScratchEntriesForKey
(scratchKey));) |
208 | 175 |
209 // Purge again. This time resources should be purgable. | 176 // Purge again. This time resources should be purgable. |
210 cache2->purgeAllUnlocked(); | 177 cache->purgeAllUnlocked(); |
211 REPORTER_ASSERT(reporter, 0 == TestResource::NumAlive()); | 178 REPORTER_ASSERT(reporter, 0 == TestResource::NumAlive()); |
212 REPORTER_ASSERT(reporter, 0 == cache2->getResourceCount()); | 179 REPORTER_ASSERT(reporter, 0 == cache->getCachedResourceCount()); |
213 SkDEBUGCODE(REPORTER_ASSERT(reporter, 0 == cache2->countScratchEntriesForKey
(scratchKey));) | 180 SkDEBUGCODE(REPORTER_ASSERT(reporter, 0 == cache2->countScratchEntriesForKey
(scratchKey));) |
214 } | 181 } |
215 | 182 |
216 static void test_duplicate_content_key(skiatest::Reporter* reporter) { | 183 static void test_duplicate_content_key(skiatest::Reporter* reporter) { |
217 SkAutoTUnref<GrContext> context(GrContext::CreateMockContext()); | 184 SkAutoTUnref<GrContext> context(GrContext::CreateMockContext()); |
218 REPORTER_ASSERT(reporter, SkToBool(context)); | 185 REPORTER_ASSERT(reporter, SkToBool(context)); |
219 if (NULL == context) { | 186 if (NULL == context) { |
220 return; | 187 return; |
221 } | 188 } |
222 context->setResourceCacheLimits(5, 30000); | 189 context->setResourceCacheLimits(5, 30000); |
223 GrResourceCache2* cache2 = context->getResourceCache2(); | 190 GrResourceCache* cache = context->getResourceCache(); |
224 cache2->purgeAllUnlocked(); | 191 cache->purgeAllUnlocked(); |
225 SkASSERT(0 == cache2->getResourceCount() && 0 == cache2->getResourceBytes())
; | 192 SkASSERT(0 == cache->getCachedResourceCount() && 0 == cache->getCachedResour
ceBytes()); |
226 | 193 |
227 GrCacheID::Domain domain = GrCacheID::GenerateDomain(); | 194 GrCacheID::Domain domain = GrCacheID::GenerateDomain(); |
228 GrCacheID::Key keyData; | 195 GrCacheID::Key keyData; |
229 memset(&keyData, 0, sizeof(keyData)); | 196 memset(&keyData, 0, sizeof(keyData)); |
230 GrResourceKey::ResourceType t = GrResourceKey::GenerateResourceType(); | 197 GrResourceKey::ResourceType t = GrResourceKey::GenerateResourceType(); |
231 GrResourceKey key(GrCacheID(domain, keyData), t, 0); | 198 GrResourceKey key(GrCacheID(domain, keyData), t, 0); |
232 | 199 |
| 200 |
233 // Create two resources that we will attempt to register with the same conte
nt key. | 201 // Create two resources that we will attempt to register with the same conte
nt key. |
234 TestResource* a = new TestResource(context->getGpu()); | 202 TestResource* a = new TestResource(context->getGpu()); |
235 TestResource* b = new TestResource(context->getGpu()); | 203 TestResource* b = new TestResource(context->getGpu()); |
236 a->setSize(11); | 204 a->setSize(11); |
237 b->setSize(12); | 205 b->setSize(12); |
238 | 206 REPORTER_ASSERT(reporter, cache->addResource(key, a)); |
239 // Can't set the same content key on two resources. | 207 // Can't add the same or another resource with the same key. |
240 REPORTER_ASSERT(reporter, a->cacheAccess().setContentKey(key)); | 208 REPORTER_ASSERT(reporter, !cache->addResource(key, a)); |
241 REPORTER_ASSERT(reporter, !b->cacheAccess().setContentKey(key)); | 209 REPORTER_ASSERT(reporter, !cache->addResource(key, b)); |
242 | 210 REPORTER_ASSERT(reporter, 1 == cache->getCachedResourceCount()); |
243 // Still have two resources because b is still reffed. | 211 REPORTER_ASSERT(reporter, a->gpuMemorySize() == cache->getCachedResourceByte
s()); |
244 REPORTER_ASSERT(reporter, 2 == cache2->getResourceCount()); | |
245 REPORTER_ASSERT(reporter, a->gpuMemorySize() + b->gpuMemorySize() == | |
246 cache2->getResourceBytes()); | |
247 REPORTER_ASSERT(reporter, 2 == TestResource::NumAlive()); | 212 REPORTER_ASSERT(reporter, 2 == TestResource::NumAlive()); |
248 | 213 |
249 b->unref(); | 214 b->unref(); |
250 // Now b should be gone. | 215 cache->purgeAllUnlocked(); |
251 REPORTER_ASSERT(reporter, 1 == cache2->getResourceCount()); | 216 a->setSize(10); |
252 REPORTER_ASSERT(reporter, a->gpuMemorySize() == cache2->getResourceBytes()); | 217 REPORTER_ASSERT(reporter, 1 == cache->getCachedResourceCount()); |
253 REPORTER_ASSERT(reporter, 1 == TestResource::NumAlive()); | 218 REPORTER_ASSERT(reporter, 1 == TestResource::NumAlive()); |
254 | 219 |
255 cache2->purgeAllUnlocked(); | |
256 REPORTER_ASSERT(reporter, 1 == cache2->getResourceCount()); | |
257 REPORTER_ASSERT(reporter, a->gpuMemorySize() == cache2->getResourceBytes()); | |
258 REPORTER_ASSERT(reporter, 1 == TestResource::NumAlive()); | |
259 | |
260 // Drop the ref on a but it isn't immediately purged as it still has a valid
scratch key. | |
261 a->unref(); | 220 a->unref(); |
262 REPORTER_ASSERT(reporter, 1 == cache2->getResourceCount()); | 221 cache->purgeAllUnlocked(); |
263 REPORTER_ASSERT(reporter, a->gpuMemorySize() == cache2->getResourceBytes()); | 222 REPORTER_ASSERT(reporter, 0 == cache->getCachedResourceCount()); |
264 REPORTER_ASSERT(reporter, 1 == TestResource::NumAlive()); | 223 REPORTER_ASSERT(reporter, 0 == cache->getCachedResourceBytes()); |
265 | |
266 cache2->purgeAllUnlocked(); | |
267 REPORTER_ASSERT(reporter, 0 == cache2->getResourceCount()); | |
268 REPORTER_ASSERT(reporter, 0 == cache2->getResourceBytes()); | |
269 REPORTER_ASSERT(reporter, 0 == TestResource::NumAlive()); | 224 REPORTER_ASSERT(reporter, 0 == TestResource::NumAlive()); |
270 } | 225 } |
271 | 226 |
272 static void test_purge_invalidated(skiatest::Reporter* reporter) { | 227 static void test_purge_invalidated(skiatest::Reporter* reporter) { |
273 SkAutoTUnref<GrContext> context(GrContext::CreateMockContext()); | 228 SkAutoTUnref<GrContext> context(GrContext::CreateMockContext()); |
274 REPORTER_ASSERT(reporter, SkToBool(context)); | 229 REPORTER_ASSERT(reporter, SkToBool(context)); |
275 if (NULL == context) { | 230 if (NULL == context) { |
276 return; | 231 return; |
277 } | 232 } |
278 | 233 |
279 GrCacheID::Domain domain = GrCacheID::GenerateDomain(); | 234 GrCacheID::Domain domain = GrCacheID::GenerateDomain(); |
280 GrCacheID::Key keyData; | 235 GrCacheID::Key keyData; |
281 memset(&keyData, 0, sizeof(keyData)); | 236 memset(&keyData, 0, sizeof(keyData)); |
282 | 237 |
283 GrResourceKey::ResourceType t = GrResourceKey::GenerateResourceType(); | 238 GrResourceKey::ResourceType t = GrResourceKey::GenerateResourceType(); |
284 | 239 |
285 keyData.fData64[0] = 1; | 240 keyData.fData64[0] = 1; |
286 GrResourceKey key1(GrCacheID(domain, keyData), t, 0); | 241 GrResourceKey key1(GrCacheID(domain, keyData), t, 0); |
287 keyData.fData64[0] = 2; | 242 keyData.fData64[0] = 2; |
288 GrResourceKey key2(GrCacheID(domain, keyData), t, 0); | 243 GrResourceKey key2(GrCacheID(domain, keyData), t, 0); |
289 keyData.fData64[0] = 3; | 244 keyData.fData64[0] = 3; |
290 GrResourceKey key3(GrCacheID(domain, keyData), t, 0); | 245 GrResourceKey key3(GrCacheID(domain, keyData), t, 0); |
291 | 246 |
292 context->setResourceCacheLimits(5, 30000); | 247 context->setResourceCacheLimits(5, 30000); |
| 248 GrResourceCache* cache = context->getResourceCache(); |
293 GrResourceCache2* cache2 = context->getResourceCache2(); | 249 GrResourceCache2* cache2 = context->getResourceCache2(); |
294 cache2->purgeAllUnlocked(); | 250 cache->purgeAllUnlocked(); |
295 SkASSERT(0 == cache2->getResourceCount() && 0 == cache2->getResourceBytes())
; | 251 SkASSERT(0 == cache->getCachedResourceCount() && 0 == cache->getCachedResour
ceBytes()); |
296 | 252 |
297 // Add three resources to the cache. | 253 // Add three resources to the cache. |
298 TestResource* a = new TestResource(context->getGpu()); | 254 TestResource* a = new TestResource(context->getGpu()); |
299 TestResource* b = new TestResource(context->getGpu()); | 255 TestResource* b = new TestResource(context->getGpu()); |
300 TestResource* c = new TestResource(context->getGpu()); | 256 TestResource* c = new TestResource(context->getGpu()); |
301 a->cacheAccess().setContentKey(key1); | 257 cache->addResource(key1, a); |
302 b->cacheAccess().setContentKey(key2); | 258 cache->addResource(key2, b); |
303 c->cacheAccess().setContentKey(key3); | 259 cache->addResource(key3, c); |
304 a->unref(); | 260 a->unref(); |
305 b->unref(); | 261 b->unref(); |
306 c->unref(); | 262 c->unref(); |
307 | 263 |
308 REPORTER_ASSERT(reporter, cache2->hasContentKey(key1)); | 264 REPORTER_ASSERT(reporter, cache2->hasContentKey(key1)); |
309 REPORTER_ASSERT(reporter, cache2->hasContentKey(key2)); | 265 REPORTER_ASSERT(reporter, cache2->hasContentKey(key2)); |
310 REPORTER_ASSERT(reporter, cache2->hasContentKey(key3)); | 266 REPORTER_ASSERT(reporter, cache2->hasContentKey(key3)); |
311 | 267 |
312 // Invalidate two of the three, they should be purged and destroyed. | 268 // Invalidate two of the three, they should be purged and destroyed. |
313 REPORTER_ASSERT(reporter, 3 == TestResource::NumAlive()); | 269 REPORTER_ASSERT(reporter, 3 == TestResource::NumAlive()); |
314 const GrResourceInvalidatedMessage msg1 = { key1 }; | 270 const GrResourceInvalidatedMessage msg1 = { key1 }; |
315 SkMessageBus<GrResourceInvalidatedMessage>::Post(msg1); | 271 SkMessageBus<GrResourceInvalidatedMessage>::Post(msg1); |
316 const GrResourceInvalidatedMessage msg2 = { key2 }; | 272 const GrResourceInvalidatedMessage msg2 = { key2 }; |
317 SkMessageBus<GrResourceInvalidatedMessage>::Post(msg2); | 273 SkMessageBus<GrResourceInvalidatedMessage>::Post(msg2); |
| 274 cache->purgeAsNeeded(); |
318 #if 0 // Disabled until reimplemented in GrResourceCache2. | 275 #if 0 // Disabled until reimplemented in GrResourceCache2. |
319 cache2->purgeAsNeeded(); | |
320 REPORTER_ASSERT(reporter, 1 == TestResource::NumAlive()); | 276 REPORTER_ASSERT(reporter, 1 == TestResource::NumAlive()); |
321 REPORTER_ASSERT(reporter, !cache2->hasContentKey(key1)); | 277 REPORTER_ASSERT(reporter, !cache2->hasContentKey(key1)); |
322 REPORTER_ASSERT(reporter, !cache2->hasContentKey(key2)); | 278 REPORTER_ASSERT(reporter, !cache2->hasContentKey(key2)); |
323 REPORTER_ASSERT(reporter, cache2->hasContentKey(key3)); | 279 REPORTER_ASSERT(reporter, cache2->hasContentKey(key3)); |
324 #endif | 280 #endif |
325 | 281 |
326 // Invalidate the third. | 282 // Invalidate the third. |
327 const GrResourceInvalidatedMessage msg3 = { key3 }; | 283 const GrResourceInvalidatedMessage msg3 = { key3 }; |
328 SkMessageBus<GrResourceInvalidatedMessage>::Post(msg3); | 284 SkMessageBus<GrResourceInvalidatedMessage>::Post(msg3); |
| 285 cache->purgeAsNeeded(); |
329 #if 0 // Disabled until reimplemented in GrResourceCache2. | 286 #if 0 // Disabled until reimplemented in GrResourceCache2. |
330 cache2->purgeAsNeeded(); | |
331 REPORTER_ASSERT(reporter, 0 == TestResource::NumAlive()); | 287 REPORTER_ASSERT(reporter, 0 == TestResource::NumAlive()); |
332 REPORTER_ASSERT(reporter, !cache2->hasContentKey(key3)); | 288 REPORTER_ASSERT(reporter, !cache2->hasContentKey(key3)); |
333 #endif | 289 #endif |
334 | |
335 cache2->purgeAllUnlocked(); | |
336 REPORTER_ASSERT(reporter, 0 == TestResource::NumAlive()); | |
337 REPORTER_ASSERT(reporter, 0 == cache2->getResourceCount()); | |
338 REPORTER_ASSERT(reporter, 0 == cache2->getResourceBytes()); | |
339 } | 290 } |
340 | 291 |
341 static void test_cache_chained_purge(skiatest::Reporter* reporter) { | 292 static void test_cache_delete_on_destruction(skiatest::Reporter* reporter) { |
342 SkAutoTUnref<GrContext> context(GrContext::CreateMockContext()); | 293 SkAutoTUnref<GrContext> context(GrContext::CreateMockContext()); |
343 REPORTER_ASSERT(reporter, SkToBool(context)); | 294 REPORTER_ASSERT(reporter, SkToBool(context)); |
344 if (NULL == context) { | 295 if (NULL == context) { |
345 return; | 296 return; |
346 } | 297 } |
347 | 298 |
348 GrCacheID::Domain domain = GrCacheID::GenerateDomain(); | 299 GrCacheID::Domain domain = GrCacheID::GenerateDomain(); |
349 GrCacheID::Key keyData; | 300 GrCacheID::Key keyData; |
350 memset(&keyData, 0, sizeof(keyData)); | 301 memset(&keyData, 0, sizeof(keyData)); |
351 GrResourceKey::ResourceType t = GrResourceKey::GenerateResourceType(); | 302 GrResourceKey::ResourceType t = GrResourceKey::GenerateResourceType(); |
352 | 303 |
353 keyData.fData64[0] = 1; | 304 keyData.fData64[0] = 1; |
354 GrResourceKey key1(GrCacheID(domain, keyData), t, 0); | 305 GrResourceKey key1(GrCacheID(domain, keyData), t, 0); |
355 | 306 |
356 keyData.fData64[0] = 2; | 307 keyData.fData64[0] = 2; |
357 GrResourceKey key2(GrCacheID(domain, keyData), t, 0); | 308 GrResourceKey key2(GrCacheID(domain, keyData), t, 0); |
358 | 309 |
359 { | 310 { |
360 context->setResourceCacheLimits(3, 30000); | 311 context->setResourceCacheLimits(3, 30000); |
361 GrResourceCache2* cache2 = context->getResourceCache2(); | 312 GrResourceCache* cache = context->getResourceCache(); |
362 cache2->purgeAllUnlocked(); | 313 cache->purgeAllUnlocked(); |
363 SkASSERT(0 == cache2->getResourceCount() && 0 == cache2->getResourceByte
s()); | 314 SkASSERT(0 == cache->getCachedResourceCount() && 0 == cache->getCachedRe
sourceBytes()); |
364 | 315 |
365 TestResource* a = new TestResource(context->getGpu()); | 316 TestResource* a = new TestResource(context->getGpu()); |
366 TestResource* b = new TestResource(context->getGpu()); | 317 TestResource* b = new TestResource(context->getGpu()); |
367 a->cacheAccess().setContentKey(key1); | 318 cache->addResource(key1, a); |
368 b->cacheAccess().setContentKey(key2); | 319 cache->addResource(key2, b); |
369 | 320 |
370 // Make a cycle | 321 a->setDeleteWhenDestroyed(cache, b); |
371 a->setUnrefWhenDestroyed(b); | 322 b->setDeleteWhenDestroyed(cache, a); |
372 b->setUnrefWhenDestroyed(a); | |
373 | |
374 REPORTER_ASSERT(reporter, 2 == TestResource::NumAlive()); | |
375 | 323 |
376 a->unref(); | 324 a->unref(); |
377 b->unref(); | 325 b->unref(); |
378 | 326 |
379 REPORTER_ASSERT(reporter, 2 == TestResource::NumAlive()); | 327 REPORTER_ASSERT(reporter, 2 == TestResource::NumAlive()); |
380 | 328 |
381 cache2->purgeAllUnlocked(); | 329 cache->purgeAllUnlocked(); |
382 REPORTER_ASSERT(reporter, 2 == TestResource::NumAlive()); | 330 REPORTER_ASSERT(reporter, 0 == TestResource::NumAlive()); |
| 331 } |
| 332 { |
| 333 context->setResourceCacheLimits(3, 30000); |
| 334 GrResourceCache* cache = context->getResourceCache(); |
| 335 cache->purgeAllUnlocked(); |
| 336 SkASSERT(0 == cache->getCachedResourceCount() && 0 == cache->getCachedRe
sourceBytes()); |
383 | 337 |
384 // Break the cycle | 338 TestResource* a = new TestResource(context->getGpu()); |
385 a->setUnrefWhenDestroyed(NULL); | 339 TestResource* b = new TestResource(context->getGpu()); |
386 REPORTER_ASSERT(reporter, 2 == TestResource::NumAlive()); | 340 cache->addResource(key1, a); |
| 341 cache->addResource(key2, b); |
387 | 342 |
388 cache2->purgeAllUnlocked(); | 343 a->setDeleteWhenDestroyed(cache, b); |
| 344 b->setDeleteWhenDestroyed(cache, a); |
| 345 |
| 346 a->unref(); |
| 347 b->unref(); |
| 348 |
| 349 cache->deleteResource(a->cacheAccess().getCacheEntry()); |
389 REPORTER_ASSERT(reporter, 0 == TestResource::NumAlive()); | 350 REPORTER_ASSERT(reporter, 0 == TestResource::NumAlive()); |
390 } | 351 } |
391 } | 352 } |
392 | 353 |
393 static void test_resource_size_changed(skiatest::Reporter* reporter) { | 354 static void test_resource_size_changed(skiatest::Reporter* reporter) { |
394 SkAutoTUnref<GrContext> context(GrContext::CreateMockContext()); | 355 SkAutoTUnref<GrContext> context(GrContext::CreateMockContext()); |
395 REPORTER_ASSERT(reporter, SkToBool(context)); | 356 REPORTER_ASSERT(reporter, SkToBool(context)); |
396 if (NULL == context) { | 357 if (NULL == context) { |
397 return; | 358 return; |
398 } | 359 } |
399 | 360 |
400 GrCacheID::Domain domain = GrCacheID::GenerateDomain(); | 361 GrCacheID::Domain domain = GrCacheID::GenerateDomain(); |
401 GrResourceKey::ResourceType t = GrResourceKey::GenerateResourceType(); | 362 GrResourceKey::ResourceType t = GrResourceKey::GenerateResourceType(); |
402 | 363 |
403 GrCacheID::Key key1Data; | 364 GrCacheID::Key key1Data; |
404 key1Data.fData64[0] = 0; | 365 key1Data.fData64[0] = 0; |
405 key1Data.fData64[1] = 0; | 366 key1Data.fData64[1] = 0; |
406 GrResourceKey key1(GrCacheID(domain, key1Data), t, 0); | 367 GrResourceKey key1(GrCacheID(domain, key1Data), t, 0); |
407 | 368 |
408 GrCacheID::Key key2Data; | 369 GrCacheID::Key key2Data; |
409 key2Data.fData64[0] = 1; | 370 key2Data.fData64[0] = 1; |
410 key2Data.fData64[1] = 0; | 371 key2Data.fData64[1] = 0; |
411 GrResourceKey key2(GrCacheID(domain, key2Data), t, 0); | 372 GrResourceKey key2(GrCacheID(domain, key2Data), t, 0); |
412 | 373 |
413 // Test changing resources sizes (both increase & decrease). | 374 // Test changing resources sizes (both increase & decrease). |
414 { | 375 { |
415 context->setResourceCacheLimits(3, 30000); | 376 context->setResourceCacheLimits(3, 30000); |
| 377 GrResourceCache* cache = context->getResourceCache(); |
416 GrResourceCache2* cache2 = context->getResourceCache2(); | 378 GrResourceCache2* cache2 = context->getResourceCache2(); |
417 cache2->purgeAllUnlocked(); | 379 cache->purgeAllUnlocked(); |
418 SkASSERT(0 == cache2->getResourceCount() && 0 == cache2->getResourceByte
s()); | 380 SkASSERT(0 == cache->getCachedResourceCount() && 0 == cache->getCachedRe
sourceBytes()); |
419 | 381 |
420 TestResource* a = new TestResource(context->getGpu()); | 382 TestResource* a = new TestResource(context->getGpu()); |
421 a->cacheAccess().setContentKey(key1); | 383 a->setSize(100); // Test didChangeGpuMemorySize() when not in the cache. |
| 384 cache->addResource(key1, a); |
422 a->unref(); | 385 a->unref(); |
423 | 386 |
424 TestResource* b = new TestResource(context->getGpu()); | 387 TestResource* b = new TestResource(context->getGpu()); |
425 b->cacheAccess().setContentKey(key2); | 388 b->setSize(100); |
| 389 cache->addResource(key2, b); |
426 b->unref(); | 390 b->unref(); |
427 | 391 |
428 REPORTER_ASSERT(reporter, 200 == cache2->getResourceBytes()); | 392 REPORTER_ASSERT(reporter, 200 == cache->getCachedResourceBytes()); |
429 REPORTER_ASSERT(reporter, 2 == cache2->getResourceCount()); | 393 REPORTER_ASSERT(reporter, 2 == cache->getCachedResourceCount()); |
430 { | 394 { |
431 SkAutoTUnref<TestResource> find2(static_cast<TestResource*>(cache2->
findAndRefContentResource(key2))); | 395 SkAutoTUnref<TestResource> find2(static_cast<TestResource*>(cache2->
findAndRefContentResource(key2))); |
432 find2->setSize(200); | 396 find2->setSize(200); |
433 SkAutoTUnref<TestResource> find1(static_cast<TestResource*>(cache2->
findAndRefContentResource(key1))); | 397 SkAutoTUnref<TestResource> find1(static_cast<TestResource*>(cache2->
findAndRefContentResource(key1))); |
434 find1->setSize(50); | 398 find1->setSize(50); |
435 } | 399 } |
436 | 400 |
437 REPORTER_ASSERT(reporter, 250 == cache2->getResourceBytes()); | 401 REPORTER_ASSERT(reporter, 250 == cache->getCachedResourceBytes()); |
438 REPORTER_ASSERT(reporter, 2 == cache2->getResourceCount()); | 402 REPORTER_ASSERT(reporter, 2 == cache->getCachedResourceCount()); |
439 } | 403 } |
440 | 404 |
441 // Test increasing a resources size beyond the cache budget. | 405 // Test increasing a resources size beyond the cache budget. |
442 { | 406 { |
443 context->setResourceCacheLimits(2, 300); | 407 context->setResourceCacheLimits(2, 300); |
| 408 GrResourceCache* cache = context->getResourceCache(); |
444 GrResourceCache2* cache2 = context->getResourceCache2(); | 409 GrResourceCache2* cache2 = context->getResourceCache2(); |
445 cache2->purgeAllUnlocked(); | 410 cache->purgeAllUnlocked(); |
446 SkASSERT(0 == cache2->getResourceCount() && 0 == cache2->getResourceByte
s()); | 411 SkASSERT(0 == cache->getCachedResourceCount() && 0 == cache->getCachedRe
sourceBytes()); |
447 | 412 |
448 TestResource* a = new TestResource(context->getGpu()); | 413 TestResource* a = new TestResource(context->getGpu()); |
449 a->setSize(100); | 414 a->setSize(100); |
450 a->cacheAccess().setContentKey(key1); | 415 cache->addResource(key1, a); |
451 a->unref(); | 416 a->unref(); |
452 | 417 |
453 TestResource* b = new TestResource(context->getGpu()); | 418 TestResource* b = new TestResource(context->getGpu()); |
454 b->setSize(100); | 419 b->setSize(100); |
455 b->cacheAccess().setContentKey(key2); | 420 cache->addResource(key2, b); |
456 b->unref(); | 421 b->unref(); |
457 | 422 |
458 REPORTER_ASSERT(reporter, 200 == cache2->getResourceBytes()); | 423 REPORTER_ASSERT(reporter, 200 == cache->getCachedResourceBytes()); |
459 REPORTER_ASSERT(reporter, 2 == cache2->getResourceCount()); | 424 REPORTER_ASSERT(reporter, 2 == cache->getCachedResourceCount()); |
460 | 425 |
461 { | 426 { |
462 SkAutoTUnref<TestResource> find2(static_cast<TestResource*>(cache2->
findAndRefContentResource(key2))); | 427 SkAutoTUnref<TestResource> find2(static_cast<TestResource*>(cache2->
findAndRefContentResource(key2))); |
463 find2->setSize(201); | 428 find2->setSize(201); |
464 } | 429 } |
465 REPORTER_ASSERT(reporter, !cache2->hasContentKey(key1)); | 430 REPORTER_ASSERT(reporter, !cache2->hasContentKey(key1)); |
466 | 431 |
467 REPORTER_ASSERT(reporter, 201 == cache2->getResourceBytes()); | 432 REPORTER_ASSERT(reporter, 201 == cache->getCachedResourceBytes()); |
468 REPORTER_ASSERT(reporter, 1 == cache2->getResourceCount()); | 433 REPORTER_ASSERT(reporter, 1 == cache->getCachedResourceCount()); |
469 } | 434 } |
470 } | 435 } |
471 | 436 |
472 //////////////////////////////////////////////////////////////////////////////// | 437 //////////////////////////////////////////////////////////////////////////////// |
473 DEF_GPUTEST(ResourceCache, reporter, factory) { | 438 DEF_GPUTEST(ResourceCache, reporter, factory) { |
474 for (int type = 0; type < GrContextFactory::kLastGLContextType; ++type) { | 439 for (int type = 0; type < GrContextFactory::kLastGLContextType; ++type) { |
475 GrContextFactory::GLContextType glType = static_cast<GrContextFactory::G
LContextType>(type); | 440 GrContextFactory::GLContextType glType = static_cast<GrContextFactory::G
LContextType>(type); |
476 if (!GrContextFactory::IsRenderingGLContext(glType)) { | 441 if (!GrContextFactory::IsRenderingGLContext(glType)) { |
477 continue; | 442 continue; |
478 } | 443 } |
479 GrContext* context = factory->get(glType); | 444 GrContext* context = factory->get(glType); |
480 if (NULL == context) { | 445 if (NULL == context) { |
481 continue; | 446 continue; |
482 } | 447 } |
483 GrSurfaceDesc desc; | 448 GrSurfaceDesc desc; |
484 desc.fConfig = kSkia8888_GrPixelConfig; | 449 desc.fConfig = kSkia8888_GrPixelConfig; |
485 desc.fFlags = kRenderTarget_GrSurfaceFlag; | 450 desc.fFlags = kRenderTarget_GrSurfaceFlag; |
486 desc.fWidth = gWidth; | 451 desc.fWidth = gWidth; |
487 desc.fHeight = gHeight; | 452 desc.fHeight = gHeight; |
488 SkImageInfo info = SkImageInfo::MakeN32Premul(gWidth, gHeight); | 453 SkImageInfo info = SkImageInfo::MakeN32Premul(gWidth, gHeight); |
489 SkAutoTUnref<SkSurface> surface(SkSurface::NewRenderTarget(context, info
)); | 454 SkAutoTUnref<SkSurface> surface(SkSurface::NewRenderTarget(context, info
)); |
490 test_cache(reporter, context, surface->getCanvas()); | 455 test_cache(reporter, context, surface->getCanvas()); |
491 } | 456 } |
492 | 457 |
493 // The below tests create their own mock contexts. | 458 // The below tests create their own mock contexts. |
494 test_no_key(reporter); | |
495 test_duplicate_content_key(reporter); | 459 test_duplicate_content_key(reporter); |
496 test_duplicate_scratch_key(reporter); | 460 test_duplicate_scratch_key(reporter); |
497 test_purge_invalidated(reporter); | 461 test_purge_invalidated(reporter); |
498 test_cache_chained_purge(reporter); | 462 test_cache_delete_on_destruction(reporter); |
499 test_resource_size_changed(reporter); | 463 test_resource_size_changed(reporter); |
500 } | 464 } |
501 | 465 |
502 #endif | 466 #endif |
OLD | NEW |