Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(18)

Side by Side Diff: chrome/browser/privacy_blacklist/blacklist_manager.cc

Issue 337025: Design changes in browser/privacy_blacklist needed to integrate (Closed)
Patch Set: fixes Created 11 years, 1 month ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
1 // Copyright (c) 2009 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2009 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 "chrome/browser/privacy_blacklist/blacklist_manager.h" 5 #include "chrome/browser/privacy_blacklist/blacklist_manager.h"
6 6
7 #include "base/message_loop.h" 7 #include "base/message_loop.h"
8 #include "base/string_util.h"
8 #include "base/task.h" 9 #include "base/task.h"
9 #include "base/thread.h" 10 #include "base/thread.h"
10 #include "chrome/browser/privacy_blacklist/blacklist.h" 11 #include "chrome/browser/privacy_blacklist/blacklist.h"
11 #include "chrome/browser/privacy_blacklist/blacklist_io.h" 12 #include "chrome/browser/privacy_blacklist/blacklist_io.h"
12 #include "chrome/browser/profile.h" 13 #include "chrome/browser/profile.h"
13 #include "chrome/common/chrome_constants.h" 14 #include "chrome/common/chrome_constants.h"
15 #include "chrome/common/notification_service.h"
14 #include "chrome/common/notification_source.h" 16 #include "chrome/common/notification_source.h"
15 #include "chrome/common/notification_type.h" 17 #include "chrome/common/notification_type.h"
16 18
17 // Base class for tasks that use BlacklistManager. It ensures that the 19 // Base class for tasks that use BlacklistManager. It ensures that the
18 // BlacklistManager won't get destroyed while we need it, and that it 20 // BlacklistManager won't get destroyed while we need it, and that it
19 // will be destroyed always on the same thread. That's why we use 21 // will be destroyed always on the same thread. That's why we use
20 // a custom Task instead of just NewRunnableMethod. 22 // a custom Task instead of just NewRunnableMethod.
21 class BlacklistManagerTask : public Task { 23 class BlacklistManagerTask : public Task {
22 public: 24 public:
23 explicit BlacklistManagerTask(BlacklistManager* manager) 25 explicit BlacklistManagerTask(BlacklistManager* manager)
24 : manager_(manager), 26 : original_loop_(MessageLoop::current()),
25 original_loop_(MessageLoop::current()) { 27 manager_(manager) {
26 DCHECK(original_loop_); 28 DCHECK(original_loop_);
27 manager->AddRef(); 29 manager->AddRef();
28 } 30 }
29 31
30 ~BlacklistManagerTask() { 32 ~BlacklistManagerTask() {
31 original_loop_->ReleaseSoon(FROM_HERE, manager_); 33 original_loop_->ReleaseSoon(FROM_HERE, manager_);
32 } 34 }
33 35
34 protected: 36 protected:
35 BlacklistManager* blacklist_manager() const { return manager_; } 37 BlacklistManager* blacklist_manager() const { return manager_; }
38
39 MessageLoop* original_loop_;
36 40
37 private: 41 private:
38 BlacklistManager* manager_; 42 BlacklistManager* manager_;
39 43
40 MessageLoop* original_loop_;
41
42 DISALLOW_COPY_AND_ASSIGN(BlacklistManagerTask); 44 DISALLOW_COPY_AND_ASSIGN(BlacklistManagerTask);
43 }; 45 };
44 46
45 BlacklistPathProvider::~BlacklistPathProvider() { 47 BlacklistPathProvider::~BlacklistPathProvider() {
46 } 48 }
47 49
48 class BlacklistManager::CompileBlacklistTask : public BlacklistManagerTask { 50 class BlacklistManager::CompileBlacklistTask : public BlacklistManagerTask {
49 public: 51 public:
50 CompileBlacklistTask(BlacklistManager* manager, 52 CompileBlacklistTask(BlacklistManager* manager,
51 const FilePath& destination_blacklist, 53 const FilePath& destination_blacklist,
52 const std::vector<FilePath>& source_blacklists) 54 const std::vector<FilePath>& source_blacklists)
53 : BlacklistManagerTask(manager), 55 : BlacklistManagerTask(manager),
54 destination_blacklist_(destination_blacklist), 56 destination_blacklist_(destination_blacklist),
55 source_blacklists_(source_blacklists) { 57 source_blacklists_(source_blacklists) {
56 } 58 }
57 59
58 virtual void Run() { 60 virtual void Run() {
59 BlacklistIO io;
60 bool success = true; 61 bool success = true;
62
63 Blacklist blacklist;
64 std::string error_string;
61 65
62 for (std::vector<FilePath>::const_iterator i = source_blacklists_.begin(); 66 for (std::vector<FilePath>::const_iterator i = source_blacklists_.begin();
63 i != source_blacklists_.end(); ++i) { 67 i != source_blacklists_.end(); ++i) {
64 if (!io.Read(*i)) { 68 if (!BlacklistIO::ReadText(&blacklist, *i, &error_string)) {
65 success = false; 69 success = false;
66 break; 70 break;
67 } 71 }
68 } 72 }
69 73
70 // Only overwrite the current compiled blacklist if we read all source 74 // Only overwrite the current compiled blacklist if we read all source
71 // files successfully. 75 // files successfully.
72 if (success) 76 if (success)
73 success = io.Write(destination_blacklist_); 77 success = BlacklistIO::WriteBinary(&blacklist, destination_blacklist_);
74 78
75 blacklist_manager()->OnBlacklistCompilationFinished(success); 79 original_loop_->PostTask(
80 FROM_HERE,
81 NewRunnableMethod(blacklist_manager(),
82 &BlacklistManager::OnBlacklistCompilationFinished,
83 success));
76 } 84 }
77 85
78 private: 86 private:
79 FilePath destination_blacklist_; 87 FilePath destination_blacklist_;
80 88
81 std::vector<FilePath> source_blacklists_; 89 std::vector<FilePath> source_blacklists_;
82 90
83 DISALLOW_COPY_AND_ASSIGN(CompileBlacklistTask); 91 DISALLOW_COPY_AND_ASSIGN(CompileBlacklistTask);
84 }; 92 };
85 93
86 class BlacklistManager::ReadBlacklistTask : public BlacklistManagerTask { 94 class BlacklistManager::ReadBlacklistTask : public BlacklistManagerTask {
87 public: 95 public:
88 ReadBlacklistTask(BlacklistManager* manager, const FilePath& blacklist_path) 96 ReadBlacklistTask(BlacklistManager* manager,
97 const FilePath& compiled_blacklist,
98 const std::vector<FilePath>& transient_blacklists)
89 : BlacklistManagerTask(manager), 99 : BlacklistManagerTask(manager),
90 blacklist_path_(blacklist_path) { 100 compiled_blacklist_(compiled_blacklist),
101 transient_blacklists_(transient_blacklists) {
91 } 102 }
92 103
93 virtual void Run() { 104 virtual void Run() {
94 Blacklist* blacklist = new Blacklist(blacklist_path_); 105 scoped_ptr<Blacklist> blacklist(new Blacklist);
95 blacklist_manager()->OnBlacklistReadFinished(blacklist); 106 if (!BlacklistIO::ReadBinary(blacklist.get(), compiled_blacklist_)) {
107 ReportReadResult(NULL);
108 return;
109 }
110
111 std::string error_string;
112 std::vector<FilePath>::const_iterator i;
113 for (i = transient_blacklists_.begin();
114 i != transient_blacklists_.end(); ++i) {
115 if (!BlacklistIO::ReadText(blacklist.get(), *i, &error_string)) {
116 ReportReadResult(NULL);
117 return;
118 }
119 }
120
121 ReportReadResult(blacklist.release());
96 } 122 }
97 123
98 private: 124 private:
99 FilePath blacklist_path_; 125 void ReportReadResult(Blacklist* blacklist) {
126 original_loop_->PostTask(
127 FROM_HERE, NewRunnableMethod(blacklist_manager(),
128 &BlacklistManager::OnBlacklistReadFinished,
129 blacklist));
130 }
131
132 FilePath compiled_blacklist_;
133 std::vector<FilePath> transient_blacklists_;
100 134
101 DISALLOW_COPY_AND_ASSIGN(ReadBlacklistTask); 135 DISALLOW_COPY_AND_ASSIGN(ReadBlacklistTask);
102 }; 136 };
103 137
104 BlacklistManager::BlacklistManager(Profile* profile, 138 BlacklistManager::BlacklistManager(Profile* profile,
139 BlacklistPathProvider* path_provider,
105 base::Thread* backend_thread) 140 base::Thread* backend_thread)
106 : compiled_blacklist_path_( 141 : first_read_finished_(false),
142 profile_(profile),
143 compiled_blacklist_path_(
107 profile->GetPath().Append(chrome::kPrivacyBlacklistFileName)), 144 profile->GetPath().Append(chrome::kPrivacyBlacklistFileName)),
108 compiling_blacklist_(false), 145 path_provider_(path_provider),
109 backend_thread_(backend_thread) { 146 backend_thread_(backend_thread) {
110 registrar_.Add(this, 147 registrar_.Add(this,
111 NotificationType::PRIVACY_BLACKLIST_PATH_PROVIDER_UPDATED, 148 NotificationType::BLACKLIST_PATH_PROVIDER_UPDATED,
112 Source<Profile>(profile)); 149 Source<Profile>(profile));
113 ReadBlacklist(); 150 ReadBlacklist();
114 } 151 }
115 152
116 void BlacklistManager::RegisterBlacklistPathProvider(
117 BlacklistPathProvider* provider) {
118 DCHECK(providers_.find(provider) == providers_.end());
119 providers_.insert(provider);
120 }
121
122 void BlacklistManager::UnregisterBlacklistPathProvider(
123 BlacklistPathProvider* provider) {
124 DCHECK(providers_.find(provider) != providers_.end());
125 providers_.erase(provider);
126 }
127
128 void BlacklistManager::Observe(NotificationType type, 153 void BlacklistManager::Observe(NotificationType type,
129 const NotificationSource& source, 154 const NotificationSource& source,
130 const NotificationDetails& details) { 155 const NotificationDetails& details) {
131 DCHECK(type == NotificationType::PRIVACY_BLACKLIST_PATH_PROVIDER_UPDATED); 156 DCHECK(type == NotificationType::BLACKLIST_PATH_PROVIDER_UPDATED);
132 CompileBlacklist(); 157 CompileBlacklist();
133 } 158 }
134 159
135 void BlacklistManager::CompileBlacklist() { 160 void BlacklistManager::CompileBlacklist() {
136 if (compiling_blacklist_) { 161 DCHECK(CalledOnValidThread());
137 // If we end up here, that means that initial compile succeeded,
138 // but then we couldn't read back the resulting Blacklist. Return early
139 // to avoid a potential infinite loop.
140 // TODO(phajdan.jr): Report the error.
141 compiling_blacklist_ = false;
142 return;
143 }
144 162
145 compiling_blacklist_ = true; 163 RunTaskOnBackendThread(new CompileBlacklistTask(
146 164 this, compiled_blacklist_path_,
147 std::vector<FilePath> source_blacklists; 165 path_provider_->GetPersistentBlacklistPaths()));
148
149 for (ProvidersSet::iterator provider = providers_.begin();
150 provider != providers_.end(); ++provider) {
151 std::vector<FilePath> provided_paths((*provider)->GetBlacklistPaths());
152 source_blacklists.insert(source_blacklists.end(),
153 provided_paths.begin(), provided_paths.end());
154 }
155
156 RunTaskOnBackendThread(new CompileBlacklistTask(this, compiled_blacklist_path_ ,
157 source_blacklists));
158 } 166 }
159 167
160 void BlacklistManager::ReadBlacklist() { 168 void BlacklistManager::ReadBlacklist() {
161 RunTaskOnBackendThread(new ReadBlacklistTask(this, compiled_blacklist_path_)); 169 DCHECK(CalledOnValidThread());
170
171 RunTaskOnBackendThread(new ReadBlacklistTask(
172 this, compiled_blacklist_path_,
173 path_provider_->GetTransientBlacklistPaths()));
162 } 174 }
163 175
164 void BlacklistManager::OnBlacklistCompilationFinished(bool success) { 176 void BlacklistManager::OnBlacklistCompilationFinished(bool success) {
177 DCHECK(CalledOnValidThread());
178
165 if (success) { 179 if (success) {
166 ReadBlacklist(); 180 ReadBlacklist();
167 } else { 181 } else {
168 // TODO(phajdan.jr): Report the error. 182 string16 error_message(ASCIIToUTF16("Blacklist compilation failed."));
183 NotificationService::current()->Notify(
184 NotificationType::BLACKLIST_MANAGER_ERROR,
185 Source<Profile>(profile_),
186 Details<string16>(&error_message));
169 } 187 }
170 } 188 }
171 189
172 void BlacklistManager::OnBlacklistReadFinished(Blacklist* blacklist) { 190 void BlacklistManager::OnBlacklistReadFinished(Blacklist* blacklist) {
173 if (blacklist->is_good()) { 191 DCHECK(CalledOnValidThread());
174 compiled_blacklist_.reset(blacklist); 192
175 compiling_blacklist_ = false; 193 if (!blacklist) {
176 } else { 194 if (!first_read_finished_) {
177 delete blacklist; 195 // If we're loading for the first time, the compiled blacklist could
178 CompileBlacklist(); 196 // just not exist. Try compiling it once.
197 first_read_finished_ = true;
198 CompileBlacklist();
199 } else {
200 string16 error_message(ASCIIToUTF16("Blacklist read failed."));
201 NotificationService::current()->Notify(
202 NotificationType::BLACKLIST_MANAGER_ERROR,
203 Source<Profile>(profile_),
204 Details<string16>(&error_message));
205 }
206 return;
179 } 207 }
208 first_read_finished_ = true;
209 compiled_blacklist_.reset(blacklist);
210
211 NotificationService::current()->Notify(
212 NotificationType::BLACKLIST_MANAGER_BLACKLIST_READ_FINISHED,
213 Source<Profile>(profile_),
214 Details<Blacklist>(blacklist));
180 } 215 }
181 216
182 void BlacklistManager::RunTaskOnBackendThread(Task* task) { 217 void BlacklistManager::RunTaskOnBackendThread(Task* task) {
183 if (backend_thread_) { 218 if (backend_thread_) {
184 backend_thread_->message_loop()->PostTask(FROM_HERE, task); 219 backend_thread_->message_loop()->PostTask(FROM_HERE, task);
185 } else { 220 } else {
186 task->Run(); 221 task->Run();
187 delete task; 222 delete task;
188 } 223 }
189 } 224 }
OLDNEW
« no previous file with comments | « chrome/browser/privacy_blacklist/blacklist_manager.h ('k') | chrome/browser/privacy_blacklist/blacklist_manager_unittest.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698