| OLD | NEW |
| 1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2012 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/extensions/api/web_request/web_request_api.h" | 5 #include "chrome/browser/extensions/api/web_request/web_request_api.h" |
| 6 | 6 |
| 7 #include <algorithm> | 7 #include <algorithm> |
| 8 | 8 |
| 9 #include "base/bind.h" | 9 #include "base/bind.h" |
| 10 #include "base/bind_helpers.h" | 10 #include "base/bind_helpers.h" |
| (...skipping 379 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 390 // NOTE(benjhayden) New APIs should not use this sub_event_name trick! It does | 390 // NOTE(benjhayden) New APIs should not use this sub_event_name trick! It does |
| 391 // not play well with event pages. See downloads.onDeterminingFilename and | 391 // not play well with event pages. See downloads.onDeterminingFilename and |
| 392 // ExtensionDownloadsEventRouter for an alternative approach. | 392 // ExtensionDownloadsEventRouter for an alternative approach. |
| 393 struct ExtensionWebRequestEventRouter::EventListener { | 393 struct ExtensionWebRequestEventRouter::EventListener { |
| 394 std::string extension_id; | 394 std::string extension_id; |
| 395 std::string extension_name; | 395 std::string extension_name; |
| 396 std::string sub_event_name; | 396 std::string sub_event_name; |
| 397 RequestFilter filter; | 397 RequestFilter filter; |
| 398 int extra_info_spec; | 398 int extra_info_spec; |
| 399 int embedder_process_id; | 399 int embedder_process_id; |
| 400 int embedder_routing_id; |
| 400 int webview_instance_id; | 401 int webview_instance_id; |
| 401 base::WeakPtr<IPC::Sender> ipc_sender; | 402 base::WeakPtr<IPC::Sender> ipc_sender; |
| 402 mutable std::set<uint64> blocked_requests; | 403 mutable std::set<uint64> blocked_requests; |
| 403 | 404 |
| 404 // Comparator to work with std::set. | 405 // Comparator to work with std::set. |
| 405 bool operator<(const EventListener& that) const { | 406 bool operator<(const EventListener& that) const { |
| 406 if (extension_id < that.extension_id) | 407 if (extension_id < that.extension_id) |
| 407 return true; | 408 return true; |
| 408 if (extension_id == that.extension_id && | 409 if (extension_id == that.extension_id && |
| 409 sub_event_name < that.sub_event_name) | 410 sub_event_name < that.sub_event_name) |
| (...skipping 755 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1165 | 1166 |
| 1166 bool ExtensionWebRequestEventRouter::AddEventListener( | 1167 bool ExtensionWebRequestEventRouter::AddEventListener( |
| 1167 void* profile, | 1168 void* profile, |
| 1168 const std::string& extension_id, | 1169 const std::string& extension_id, |
| 1169 const std::string& extension_name, | 1170 const std::string& extension_name, |
| 1170 const std::string& event_name, | 1171 const std::string& event_name, |
| 1171 const std::string& sub_event_name, | 1172 const std::string& sub_event_name, |
| 1172 const RequestFilter& filter, | 1173 const RequestFilter& filter, |
| 1173 int extra_info_spec, | 1174 int extra_info_spec, |
| 1174 int embedder_process_id, | 1175 int embedder_process_id, |
| 1176 int embedder_routing_id, |
| 1175 int webview_instance_id, | 1177 int webview_instance_id, |
| 1176 base::WeakPtr<IPC::Sender> ipc_sender) { | 1178 base::WeakPtr<IPC::Sender> ipc_sender) { |
| 1177 | 1179 |
| 1178 if (!IsWebRequestEvent(event_name)) | 1180 if (!IsWebRequestEvent(event_name)) |
| 1179 return false; | 1181 return false; |
| 1180 | 1182 |
| 1181 EventListener listener; | 1183 EventListener listener; |
| 1182 listener.extension_id = extension_id; | 1184 listener.extension_id = extension_id; |
| 1183 listener.extension_name = extension_name; | 1185 listener.extension_name = extension_name; |
| 1184 listener.sub_event_name = sub_event_name; | 1186 listener.sub_event_name = sub_event_name; |
| 1185 listener.filter = filter; | 1187 listener.filter = filter; |
| 1186 listener.extra_info_spec = extra_info_spec; | 1188 listener.extra_info_spec = extra_info_spec; |
| 1187 listener.ipc_sender = ipc_sender; | 1189 listener.ipc_sender = ipc_sender; |
| 1188 listener.embedder_process_id = embedder_process_id; | 1190 listener.embedder_process_id = embedder_process_id; |
| 1191 listener.embedder_routing_id = embedder_routing_id; |
| 1189 listener.webview_instance_id = webview_instance_id; | 1192 listener.webview_instance_id = webview_instance_id; |
| 1190 if (listener.webview_instance_id) | 1193 if (listener.webview_instance_id) |
| 1191 RecordAction(content::UserMetricsAction("WebView.WebRequest.AddListener")); | 1194 RecordAction(content::UserMetricsAction("WebView.WebRequest.AddListener")); |
| 1192 | 1195 |
| 1193 if (listeners_[profile][event_name].count(listener) != 0u) { | 1196 if (listeners_[profile][event_name].count(listener) != 0u) { |
| 1194 // This is likely an abuse of the API by a malicious extension. | 1197 // This is likely an abuse of the API by a malicious extension. |
| 1195 return false; | 1198 return false; |
| 1196 } | 1199 } |
| 1197 listeners_[profile][event_name].insert(listener); | 1200 listeners_[profile][event_name].insert(listener); |
| 1198 return true; | 1201 return true; |
| (...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1231 | 1234 |
| 1232 listeners_[profile][event_name].erase(listener); | 1235 listeners_[profile][event_name].erase(listener); |
| 1233 | 1236 |
| 1234 helpers::ClearCacheOnNavigation(); | 1237 helpers::ClearCacheOnNavigation(); |
| 1235 } | 1238 } |
| 1236 | 1239 |
| 1237 void ExtensionWebRequestEventRouter::RemoveWebViewEventListeners( | 1240 void ExtensionWebRequestEventRouter::RemoveWebViewEventListeners( |
| 1238 void* profile, | 1241 void* profile, |
| 1239 const std::string& extension_id, | 1242 const std::string& extension_id, |
| 1240 int embedder_process_id, | 1243 int embedder_process_id, |
| 1244 int embedder_routing_id, |
| 1241 int webview_instance_id) { | 1245 int webview_instance_id) { |
| 1242 // Iterate over all listeners of all WebRequest events to delete | 1246 // Iterate over all listeners of all WebRequest events to delete |
| 1243 // any listeners that belong to the provided <webview>. | 1247 // any listeners that belong to the provided <webview>. |
| 1244 ListenerMapForProfile& map_for_profile = listeners_[profile]; | 1248 ListenerMapForProfile& map_for_profile = listeners_[profile]; |
| 1245 for (ListenerMapForProfile::iterator event_iter = map_for_profile.begin(); | 1249 for (ListenerMapForProfile::iterator event_iter = map_for_profile.begin(); |
| 1246 event_iter != map_for_profile.end(); ++event_iter) { | 1250 event_iter != map_for_profile.end(); ++event_iter) { |
| 1247 std::vector<EventListener> listeners_to_delete; | 1251 std::vector<EventListener> listeners_to_delete; |
| 1248 std::set<EventListener>& listeners = event_iter->second; | 1252 std::set<EventListener>& listeners = event_iter->second; |
| 1249 for (std::set<EventListener>::iterator listener_iter = listeners.begin(); | 1253 for (std::set<EventListener>::iterator listener_iter = listeners.begin(); |
| 1250 listener_iter != listeners.end(); ++listener_iter) { | 1254 listener_iter != listeners.end(); ++listener_iter) { |
| 1251 const EventListener& listener = *listener_iter; | 1255 const EventListener& listener = *listener_iter; |
| 1256 // TODO(fsamuel): Investigate making <webview> instance IDs unique within |
| 1257 // a process. |
| 1252 if (listener.embedder_process_id == embedder_process_id && | 1258 if (listener.embedder_process_id == embedder_process_id && |
| 1259 listener.embedder_routing_id == embedder_routing_id && |
| 1253 listener.webview_instance_id == webview_instance_id) | 1260 listener.webview_instance_id == webview_instance_id) |
| 1254 listeners_to_delete.push_back(listener); | 1261 listeners_to_delete.push_back(listener); |
| 1255 } | 1262 } |
| 1256 for (size_t i = 0; i < listeners_to_delete.size(); ++i) { | 1263 for (size_t i = 0; i < listeners_to_delete.size(); ++i) { |
| 1257 EventListener& listener = listeners_to_delete[i]; | 1264 EventListener& listener = listeners_to_delete[i]; |
| 1258 content::BrowserThread::PostTask( | 1265 content::BrowserThread::PostTask( |
| 1259 content::BrowserThread::UI, | 1266 content::BrowserThread::UI, |
| 1260 FROM_HERE, | 1267 FROM_HERE, |
| 1261 base::Bind(&RemoveEventListenerOnUI, | 1268 base::Bind(&RemoveEventListenerOnUI, |
| 1262 profile, | 1269 profile, |
| (...skipping 101 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1364 for (std::set<EventListener>::iterator it = listeners.begin(); | 1371 for (std::set<EventListener>::iterator it = listeners.begin(); |
| 1365 it != listeners.end(); ++it) { | 1372 it != listeners.end(); ++it) { |
| 1366 if (!it->ipc_sender.get()) { | 1373 if (!it->ipc_sender.get()) { |
| 1367 // The IPC sender has been deleted. This listener will be removed soon | 1374 // The IPC sender has been deleted. This listener will be removed soon |
| 1368 // via a call to RemoveEventListener. For now, just skip it. | 1375 // via a call to RemoveEventListener. For now, just skip it. |
| 1369 continue; | 1376 continue; |
| 1370 } | 1377 } |
| 1371 | 1378 |
| 1372 if (is_guest && | 1379 if (is_guest && |
| 1373 (it->embedder_process_id != webview_info.embedder_process_id || | 1380 (it->embedder_process_id != webview_info.embedder_process_id || |
| 1381 it->embedder_routing_id != webview_info.embedder_routing_id || |
| 1374 it->webview_instance_id != webview_info.instance_id)) | 1382 it->webview_instance_id != webview_info.instance_id)) |
| 1375 continue; | 1383 continue; |
| 1376 | 1384 |
| 1377 if (!it->filter.urls.is_empty() && !it->filter.urls.MatchesURL(url)) | 1385 if (!it->filter.urls.is_empty() && !it->filter.urls.MatchesURL(url)) |
| 1378 continue; | 1386 continue; |
| 1379 if (it->filter.tab_id != -1 && tab_id != it->filter.tab_id) | 1387 if (it->filter.tab_id != -1 && tab_id != it->filter.tab_id) |
| 1380 continue; | 1388 continue; |
| 1381 if (it->filter.window_id != -1 && window_id != it->filter.window_id) | 1389 if (it->filter.window_id != -1 && window_id != it->filter.window_id) |
| 1382 continue; | 1390 continue; |
| 1383 if (!it->filter.types.empty() && | 1391 if (!it->filter.types.empty() && |
| (...skipping 688 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2072 std::string sub_event_name; | 2080 std::string sub_event_name; |
| 2073 EXTENSION_FUNCTION_VALIDATE(args_->GetString(4, &sub_event_name)); | 2081 EXTENSION_FUNCTION_VALIDATE(args_->GetString(4, &sub_event_name)); |
| 2074 | 2082 |
| 2075 int webview_instance_id = 0; | 2083 int webview_instance_id = 0; |
| 2076 EXTENSION_FUNCTION_VALIDATE(args_->GetInteger(5, &webview_instance_id)); | 2084 EXTENSION_FUNCTION_VALIDATE(args_->GetInteger(5, &webview_instance_id)); |
| 2077 | 2085 |
| 2078 base::WeakPtr<ChromeRenderMessageFilter> ipc_sender = ipc_sender_weak(); | 2086 base::WeakPtr<ChromeRenderMessageFilter> ipc_sender = ipc_sender_weak(); |
| 2079 | 2087 |
| 2080 int embedder_process_id = | 2088 int embedder_process_id = |
| 2081 ipc_sender.get() ? ipc_sender->render_process_id() : -1; | 2089 ipc_sender.get() ? ipc_sender->render_process_id() : -1; |
| 2090 int embedder_routing_id = routing_id(); |
| 2082 | 2091 |
| 2083 const Extension* extension = | 2092 const Extension* extension = |
| 2084 extension_info_map()->extensions().GetByID(extension_id()); | 2093 extension_info_map()->extensions().GetByID(extension_id()); |
| 2085 std::string extension_name = extension ? extension->name() : extension_id(); | 2094 std::string extension_name = extension ? extension->name() : extension_id(); |
| 2086 | 2095 |
| 2087 bool is_guest = webview_instance_id != 0; | 2096 bool is_guest = webview_instance_id != 0; |
| 2088 // We check automatically whether the extension has the 'webRequest' | 2097 // We check automatically whether the extension has the 'webRequest' |
| 2089 // permission. For blocking calls we require the additional permission | 2098 // permission. For blocking calls we require the additional permission |
| 2090 // 'webRequestBlocking'. | 2099 // 'webRequestBlocking'. |
| 2091 if ((!is_guest && extra_info_spec & | 2100 if ((!is_guest && extra_info_spec & |
| (...skipping 14 matching lines...) Expand all Loading... |
| 2106 if (!is_guest && extensions::PermissionsData::GetEffectiveHostPermissions( | 2115 if (!is_guest && extensions::PermissionsData::GetEffectiveHostPermissions( |
| 2107 extension).is_empty()) { | 2116 extension).is_empty()) { |
| 2108 error_ = keys::kHostPermissionsRequired; | 2117 error_ = keys::kHostPermissionsRequired; |
| 2109 return false; | 2118 return false; |
| 2110 } | 2119 } |
| 2111 | 2120 |
| 2112 bool success = | 2121 bool success = |
| 2113 ExtensionWebRequestEventRouter::GetInstance()->AddEventListener( | 2122 ExtensionWebRequestEventRouter::GetInstance()->AddEventListener( |
| 2114 profile_id(), extension_id(), extension_name, | 2123 profile_id(), extension_id(), extension_name, |
| 2115 event_name, sub_event_name, filter, extra_info_spec, | 2124 event_name, sub_event_name, filter, extra_info_spec, |
| 2116 embedder_process_id, webview_instance_id, ipc_sender_weak()); | 2125 embedder_process_id, embedder_routing_id, webview_instance_id, |
| 2126 ipc_sender_weak()); |
| 2117 EXTENSION_FUNCTION_VALIDATE(success); | 2127 EXTENSION_FUNCTION_VALIDATE(success); |
| 2118 | 2128 |
| 2119 helpers::ClearCacheOnNavigation(); | 2129 helpers::ClearCacheOnNavigation(); |
| 2120 | 2130 |
| 2121 BrowserThread::PostTask(BrowserThread::UI, FROM_HERE, base::Bind( | 2131 BrowserThread::PostTask(BrowserThread::UI, FROM_HERE, base::Bind( |
| 2122 &helpers::NotifyWebRequestAPIUsed, | 2132 &helpers::NotifyWebRequestAPIUsed, |
| 2123 profile_id(), make_scoped_refptr(GetExtension()))); | 2133 profile_id(), make_scoped_refptr(GetExtension()))); |
| 2124 | 2134 |
| 2125 return true; | 2135 return true; |
| 2126 } | 2136 } |
| (...skipping 159 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2286 } else if ((*it)->name().find("AdBlock") != std::string::npos) { | 2296 } else if ((*it)->name().find("AdBlock") != std::string::npos) { |
| 2287 adblock = true; | 2297 adblock = true; |
| 2288 } else { | 2298 } else { |
| 2289 other = true; | 2299 other = true; |
| 2290 } | 2300 } |
| 2291 } | 2301 } |
| 2292 } | 2302 } |
| 2293 | 2303 |
| 2294 host->Send(new ExtensionMsg_UsingWebRequestAPI(adblock, adblock_plus, other)); | 2304 host->Send(new ExtensionMsg_UsingWebRequestAPI(adblock, adblock_plus, other)); |
| 2295 } | 2305 } |
| OLD | NEW |