OLD | NEW |
---|---|
1 // Copyright 2015 The Chromium Authors. All rights reserved. | 1 // Copyright 2015 The Chromium 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 #include "components/browsing_data/storage_partition_http_cache_data_remover.h" | 5 #include "components/browsing_data/storage_partition_http_cache_data_remover.h" |
6 | 6 |
7 #include "content/public/browser/browser_thread.h" | 7 #include "content/public/browser/browser_thread.h" |
8 #include "content/public/browser/storage_partition.h" | 8 #include "content/public/browser/storage_partition.h" |
9 #include "net/base/sdch_manager.h" | 9 #include "net/base/sdch_manager.h" |
10 #include "net/disk_cache/blockfile/backend_impl.h" | |
10 #include "net/disk_cache/disk_cache.h" | 11 #include "net/disk_cache/disk_cache.h" |
12 #include "net/disk_cache/memory/mem_backend_impl.h" | |
13 #include "net/disk_cache/simple/simple_backend_impl.h" | |
11 #include "net/http/http_cache.h" | 14 #include "net/http/http_cache.h" |
12 #include "net/url_request/url_request_context.h" | 15 #include "net/url_request/url_request_context.h" |
13 #include "net/url_request/url_request_context_getter.h" | 16 #include "net/url_request/url_request_context_getter.h" |
14 | 17 |
15 using content::BrowserThread; | 18 using content::BrowserThread; |
16 | 19 |
17 namespace browsing_data { | 20 namespace browsing_data { |
18 | 21 |
19 StoragePartitionHttpCacheDataRemover::StoragePartitionHttpCacheDataRemover( | 22 StoragePartitionHttpCacheDataRemover::StoragePartitionHttpCacheDataRemover( |
20 base::Time delete_begin, | 23 base::Time delete_begin, |
21 base::Time delete_end, | 24 base::Time delete_end, |
22 net::URLRequestContextGetter* main_context_getter, | 25 net::URLRequestContextGetter* main_context_getter, |
23 net::URLRequestContextGetter* media_context_getter) | 26 net::URLRequestContextGetter* media_context_getter) |
24 : delete_begin_(delete_begin), | 27 : delete_begin_(delete_begin), |
25 delete_end_(delete_end), | 28 delete_end_(delete_end), |
26 main_context_getter_(main_context_getter), | 29 main_context_getter_(main_context_getter), |
27 media_context_getter_(media_context_getter), | 30 media_context_getter_(media_context_getter), |
28 next_cache_state_(STATE_NONE), | 31 next_cache_state_(STATE_NONE), |
29 cache_(nullptr) { | 32 cache_(nullptr), |
33 count_only_(false), | |
34 calculation_result_(0) { | |
30 } | 35 } |
31 | 36 |
32 StoragePartitionHttpCacheDataRemover::~StoragePartitionHttpCacheDataRemover() { | 37 StoragePartitionHttpCacheDataRemover::~StoragePartitionHttpCacheDataRemover() { |
33 } | 38 } |
34 | 39 |
35 // static. | 40 // static. |
36 StoragePartitionHttpCacheDataRemover* | 41 StoragePartitionHttpCacheDataRemover* |
37 StoragePartitionHttpCacheDataRemover::CreateForRange( | 42 StoragePartitionHttpCacheDataRemover::CreateForRange( |
38 content::StoragePartition* storage_partition, | 43 content::StoragePartition* storage_partition, |
39 base::Time delete_begin, | 44 base::Time delete_begin, |
40 base::Time delete_end) { | 45 base::Time delete_end) { |
41 return new StoragePartitionHttpCacheDataRemover( | 46 return new StoragePartitionHttpCacheDataRemover( |
42 delete_begin, delete_end, storage_partition->GetURLRequestContext(), | 47 delete_begin, delete_end, storage_partition->GetURLRequestContext(), |
43 storage_partition->GetMediaURLRequestContext()); | 48 storage_partition->GetMediaURLRequestContext()); |
44 } | 49 } |
45 | 50 |
46 void StoragePartitionHttpCacheDataRemover::Remove( | 51 void StoragePartitionHttpCacheDataRemover::Remove( |
47 const base::Closure& done_callback) { | 52 const base::Closure& done_callback) { |
48 DCHECK_CURRENTLY_ON(BrowserThread::UI); | 53 DCHECK_CURRENTLY_ON(BrowserThread::UI); |
49 DCHECK(!done_callback.is_null()); | 54 DCHECK(!done_callback.is_null()); |
50 done_callback_ = done_callback; | 55 done_callback_ = done_callback; |
56 count_only_ = false; | |
51 | 57 |
52 BrowserThread::PostTask( | 58 BrowserThread::PostTask( |
53 BrowserThread::IO, FROM_HERE, | 59 BrowserThread::IO, FROM_HERE, |
60 base::Bind( | |
61 &StoragePartitionHttpCacheDataRemover::ClearHttpCacheOnIOThread, | |
62 base::Unretained(this))); | |
63 } | |
64 | |
65 void StoragePartitionHttpCacheDataRemover::Count( | |
66 const net::Int64CompletionCallback& result_callback) { | |
67 DCHECK_CURRENTLY_ON(BrowserThread::UI); | |
68 DCHECK(!result_callback.is_null()); | |
69 result_callback_ = result_callback; | |
70 calculation_result_ = 0; | |
71 count_only_ = true; | |
72 | |
73 BrowserThread::PostTask( | |
74 BrowserThread::IO, FROM_HERE, | |
54 base::Bind( | 75 base::Bind( |
55 &StoragePartitionHttpCacheDataRemover::ClearHttpCacheOnIOThread, | 76 &StoragePartitionHttpCacheDataRemover::ClearHttpCacheOnIOThread, |
Mike West
2015/09/02 11:50:13
This feels pretty hacky. Why do we call `::ClearHt
msramek
2015/09/02 19:22:25
I duplicated the methods now. It's less hacky, but
| |
56 base::Unretained(this))); | 77 base::Unretained(this))); |
57 } | 78 } |
58 | 79 |
59 void StoragePartitionHttpCacheDataRemover::ClearHttpCacheOnIOThread() { | 80 void StoragePartitionHttpCacheDataRemover::ClearHttpCacheOnIOThread() { |
60 DCHECK_CURRENTLY_ON(BrowserThread::IO); | 81 DCHECK_CURRENTLY_ON(BrowserThread::IO); |
61 next_cache_state_ = STATE_NONE; | 82 next_cache_state_ = STATE_NONE; |
62 DCHECK_EQ(STATE_NONE, next_cache_state_); | 83 DCHECK_EQ(STATE_NONE, next_cache_state_); |
63 DCHECK(main_context_getter_.get()); | 84 DCHECK(main_context_getter_.get()); |
64 DCHECK(media_context_getter_.get()); | 85 DCHECK(media_context_getter_.get()); |
65 | 86 |
66 next_cache_state_ = STATE_CREATE_MAIN; | 87 next_cache_state_ = STATE_CREATE_MAIN; |
67 DoClearCache(net::OK); | 88 DoClearCache(net::OK); |
68 } | 89 } |
69 | 90 |
70 void StoragePartitionHttpCacheDataRemover::ClearedHttpCache() { | 91 void StoragePartitionHttpCacheDataRemover::ClearedHttpCache() { |
71 DCHECK_CURRENTLY_ON(BrowserThread::UI); | 92 DCHECK_CURRENTLY_ON(BrowserThread::UI); |
72 done_callback_.Run(); | 93 if (count_only_) |
94 result_callback_.Run(calculation_result_); | |
95 else | |
96 done_callback_.Run(); | |
73 base::MessageLoop::current()->DeleteSoon(FROM_HERE, this); | 97 base::MessageLoop::current()->DeleteSoon(FROM_HERE, this); |
74 } | 98 } |
75 | 99 |
76 // The expected state sequence is STATE_NONE --> STATE_CREATE_MAIN --> | 100 // The expected state sequence is STATE_NONE --> STATE_CREATE_MAIN --> |
77 // STATE_DELETE_MAIN --> STATE_CREATE_MEDIA --> STATE_DELETE_MEDIA --> | 101 // STATE_DELETE_MAIN --> STATE_CREATE_MEDIA --> STATE_DELETE_MEDIA --> |
78 // STATE_DONE, and any errors are ignored. | 102 // STATE_DONE, and any errors are ignored. |
79 void StoragePartitionHttpCacheDataRemover::DoClearCache(int rv) { | 103 void StoragePartitionHttpCacheDataRemover::DoClearCache(int rv) { |
80 DCHECK_NE(STATE_NONE, next_cache_state_); | 104 DCHECK_NE(STATE_NONE, next_cache_state_); |
81 | 105 |
82 while (rv != net::ERR_IO_PENDING && next_cache_state_ != STATE_NONE) { | 106 while (rv != net::ERR_IO_PENDING && next_cache_state_ != STATE_NONE) { |
83 switch (next_cache_state_) { | 107 switch (next_cache_state_) { |
84 case STATE_CREATE_MAIN: | 108 case STATE_CREATE_MAIN: |
85 case STATE_CREATE_MEDIA: { | 109 case STATE_CREATE_MEDIA: { |
86 // Get a pointer to the cache. | 110 // Get a pointer to the cache. |
87 net::URLRequestContextGetter* getter = | 111 net::URLRequestContextGetter* getter = |
88 (next_cache_state_ == STATE_CREATE_MAIN) | 112 (next_cache_state_ == STATE_CREATE_MAIN) |
89 ? main_context_getter_.get() | 113 ? main_context_getter_.get() |
90 : media_context_getter_.get(); | 114 : media_context_getter_.get(); |
91 net::HttpCache* http_cache = getter->GetURLRequestContext() | 115 net::HttpCache* http_cache = getter->GetURLRequestContext() |
92 ->http_transaction_factory() | 116 ->http_transaction_factory() |
93 ->GetCache(); | 117 ->GetCache(); |
94 | 118 |
95 next_cache_state_ = (next_cache_state_ == STATE_CREATE_MAIN) | 119 next_cache_state_ = (next_cache_state_ == STATE_CREATE_MAIN) |
96 ? STATE_DELETE_MAIN | 120 ? STATE_DELETE_MAIN |
97 : STATE_DELETE_MEDIA; | 121 : STATE_DELETE_MEDIA; |
98 | 122 |
99 // Clear QUIC server information from memory and the disk cache. | 123 if (!count_only_) { |
100 http_cache->GetSession() | 124 // Clear QUIC server information from memory and the disk cache. |
101 ->quic_stream_factory() | 125 http_cache->GetSession() |
102 ->ClearCachedStatesInCryptoConfig(); | 126 ->quic_stream_factory() |
127 ->ClearCachedStatesInCryptoConfig(); | |
103 | 128 |
104 // Clear SDCH dictionary state. | 129 // Clear SDCH dictionary state. |
105 net::SdchManager* sdch_manager = | 130 net::SdchManager* sdch_manager = |
106 getter->GetURLRequestContext()->sdch_manager(); | 131 getter->GetURLRequestContext()->sdch_manager(); |
107 // The test is probably overkill, since chrome should always have an | 132 // The test is probably overkill, since chrome should always have an |
108 // SdchManager. But in general the URLRequestContext is *not* | 133 // SdchManager. But in general the URLRequestContext is *not* |
109 // guaranteed to have an SdchManager, so checking is wise. | 134 // guaranteed to have an SdchManager, so checking is wise. |
110 if (sdch_manager) | 135 if (sdch_manager) |
111 sdch_manager->ClearData(); | 136 sdch_manager->ClearData(); |
137 } | |
112 | 138 |
113 rv = http_cache->GetBackend( | 139 rv = http_cache->GetBackend( |
114 &cache_, | 140 &cache_, |
115 base::Bind(&StoragePartitionHttpCacheDataRemover::DoClearCache, | 141 base::Bind(&StoragePartitionHttpCacheDataRemover::DoClearCache, |
116 base::Unretained(this))); | 142 base::Unretained(this))); |
117 break; | 143 break; |
118 } | 144 } |
119 case STATE_DELETE_MAIN: | 145 case STATE_DELETE_MAIN: |
120 case STATE_DELETE_MEDIA: { | 146 case STATE_DELETE_MEDIA: { |
121 next_cache_state_ = (next_cache_state_ == STATE_DELETE_MAIN) | 147 next_cache_state_ = (next_cache_state_ == STATE_DELETE_MAIN) |
122 ? STATE_CREATE_MEDIA | 148 ? STATE_CREATE_MEDIA |
123 : STATE_DONE; | 149 : STATE_DONE; |
124 | 150 |
125 // |cache_| can be null if it cannot be initialized. | 151 // |cache_| can be null if it cannot be initialized. |
126 if (cache_) { | 152 if (cache_) { |
127 if (delete_begin_.is_null()) { | 153 if (delete_begin_.is_null()) { |
128 rv = cache_->DoomAllEntries( | 154 if (count_only_) { |
129 base::Bind(&StoragePartitionHttpCacheDataRemover::DoClearCache, | 155 // TODO(msramek): Implement analogous |CalculateSizeOfAllEntries|. |
130 base::Unretained(this))); | 156 rv = cache_->CalculateSizeOfEntriesBetween( |
157 base::Time(), base::Time::Max(), | |
158 base::Bind( | |
159 &StoragePartitionHttpCacheDataRemover:: | |
160 OnCalculationComplete, | |
161 base::Unretained(this))); | |
162 } else { | |
163 rv = cache_->DoomAllEntries(base::Bind( | |
164 &StoragePartitionHttpCacheDataRemover::DoClearCache, | |
165 base::Unretained(this))); | |
166 } | |
131 } else { | 167 } else { |
132 rv = cache_->DoomEntriesBetween( | 168 if (count_only_) { |
133 delete_begin_, delete_end_, | 169 rv = cache_->CalculateSizeOfEntriesBetween( |
134 base::Bind(&StoragePartitionHttpCacheDataRemover::DoClearCache, | 170 delete_begin_, delete_end_, |
135 base::Unretained(this))); | 171 base::Bind( |
172 &StoragePartitionHttpCacheDataRemover:: | |
173 OnCalculationComplete, | |
174 base::Unretained(this))); | |
175 } else { | |
176 rv = cache_->DoomEntriesBetween( | |
177 delete_begin_, delete_end_, | |
178 base::Bind( | |
179 &StoragePartitionHttpCacheDataRemover::DoClearCache, | |
180 base::Unretained(this))); | |
181 } | |
136 } | 182 } |
137 cache_ = NULL; | 183 cache_ = NULL; |
138 } | 184 } |
139 break; | 185 break; |
140 } | 186 } |
141 case STATE_DONE: { | 187 case STATE_DONE: { |
142 cache_ = NULL; | 188 cache_ = NULL; |
143 next_cache_state_ = STATE_NONE; | 189 next_cache_state_ = STATE_NONE; |
144 | 190 |
145 // Notify the UI thread that we are done. | 191 // Notify the UI thread that we are done. |
146 BrowserThread::PostTask( | 192 BrowserThread::PostTask( |
147 BrowserThread::UI, FROM_HERE, | 193 BrowserThread::UI, FROM_HERE, |
148 base::Bind(&StoragePartitionHttpCacheDataRemover::ClearedHttpCache, | 194 base::Bind(&StoragePartitionHttpCacheDataRemover::ClearedHttpCache, |
149 base::Unretained(this))); | 195 base::Unretained(this))); |
150 return; | 196 return; |
151 } | 197 } |
152 default: { | 198 default: { |
153 NOTREACHED() << "bad state"; | 199 NOTREACHED() << "bad state"; |
154 next_cache_state_ = STATE_NONE; // Stop looping. | 200 next_cache_state_ = STATE_NONE; // Stop looping. |
155 return; | 201 return; |
156 } | 202 } |
157 } | 203 } |
158 } | 204 } |
159 } | 205 } |
160 | 206 |
207 void StoragePartitionHttpCacheDataRemover::OnCalculationComplete(int rv) { | |
208 // If the calculation was successful, add the size to the sum. If it was not, | |
209 // finish and return the error code. | |
210 if (rv < 0) { | |
211 calculation_result_ = rv; | |
212 next_cache_state_ = STATE_DONE; | |
213 DoClearCache(rv); | |
214 } else { | |
215 calculation_result_ += rv; | |
216 DoClearCache(net::OK); | |
217 } | |
218 } | |
219 | |
161 } // namespace browsing_data | 220 } // namespace browsing_data |
OLD | NEW |