| 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 "extensions/browser/api/web_request/web_request_api_helpers.h" | 5 #include "extensions/browser/api/web_request/web_request_api_helpers.h" |
| 6 | 6 |
| 7 #include <stddef.h> | 7 #include <stddef.h> |
| 8 #include <stdint.h> | 8 #include <stdint.h> |
| 9 | 9 |
| 10 #include <algorithm> | 10 #include <algorithm> |
| (...skipping 399 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 410 } | 410 } |
| 411 | 411 |
| 412 // Helper function for MergeRedirectUrlOfResponses() that allows ignoring | 412 // Helper function for MergeRedirectUrlOfResponses() that allows ignoring |
| 413 // all redirects but those to data:// urls and about:blank. This is important | 413 // all redirects but those to data:// urls and about:blank. This is important |
| 414 // to treat these URLs as "cancel urls", i.e. URLs that extensions redirect | 414 // to treat these URLs as "cancel urls", i.e. URLs that extensions redirect |
| 415 // to if they want to express that they want to cancel a request. This reduces | 415 // to if they want to express that they want to cancel a request. This reduces |
| 416 // the number of conflicts that we need to flag, as canceling is considered | 416 // the number of conflicts that we need to flag, as canceling is considered |
| 417 // a higher precedence operation that redirects. | 417 // a higher precedence operation that redirects. |
| 418 // Returns whether a redirect occurred. | 418 // Returns whether a redirect occurred. |
| 419 static bool MergeRedirectUrlOfResponsesHelper( | 419 static bool MergeRedirectUrlOfResponsesHelper( |
| 420 const GURL& url, |
| 420 const EventResponseDeltas& deltas, | 421 const EventResponseDeltas& deltas, |
| 421 GURL* new_url, | 422 GURL* new_url, |
| 422 extensions::WarningSet* conflicting_extensions, | 423 extensions::WarningSet* conflicting_extensions, |
| 423 const net::NetLogWithSource* net_log, | 424 const net::NetLogWithSource* net_log, |
| 424 bool consider_only_cancel_scheme_urls) { | 425 bool consider_only_cancel_scheme_urls) { |
| 426 // Redirecting WebSocket handshake request is prohibited. |
| 427 if (url.SchemeIsWSOrWSS()) |
| 428 return false; |
| 429 |
| 425 bool redirected = false; | 430 bool redirected = false; |
| 426 | 431 |
| 427 // Extension that determines the |new_url|. | 432 // Extension that determines the |new_url|. |
| 428 std::string winning_extension_id; | 433 std::string winning_extension_id; |
| 429 EventResponseDeltas::const_iterator delta; | 434 EventResponseDeltas::const_iterator delta; |
| 430 for (delta = deltas.begin(); delta != deltas.end(); ++delta) { | 435 for (delta = deltas.begin(); delta != deltas.end(); ++delta) { |
| 431 if ((*delta)->new_url.is_empty()) | 436 if ((*delta)->new_url.is_empty()) |
| 432 continue; | 437 continue; |
| 433 if (consider_only_cancel_scheme_urls && | 438 if (consider_only_cancel_scheme_urls && |
| 434 !(*delta)->new_url.SchemeIs(url::kDataScheme) && | 439 !(*delta)->new_url.SchemeIs(url::kDataScheme) && |
| (...skipping 16 matching lines...) Expand all Loading... |
| 451 (*delta)->new_url, | 456 (*delta)->new_url, |
| 452 *new_url)); | 457 *new_url)); |
| 453 net_log->AddEvent( | 458 net_log->AddEvent( |
| 454 net::NetLogEventType::CHROME_EXTENSION_IGNORED_DUE_TO_CONFLICT, | 459 net::NetLogEventType::CHROME_EXTENSION_IGNORED_DUE_TO_CONFLICT, |
| 455 CreateNetLogExtensionIdCallback(delta->get())); | 460 CreateNetLogExtensionIdCallback(delta->get())); |
| 456 } | 461 } |
| 457 } | 462 } |
| 458 return redirected; | 463 return redirected; |
| 459 } | 464 } |
| 460 | 465 |
| 461 void MergeRedirectUrlOfResponses(const EventResponseDeltas& deltas, | 466 void MergeRedirectUrlOfResponses(const GURL& url, |
| 467 const EventResponseDeltas& deltas, |
| 462 GURL* new_url, | 468 GURL* new_url, |
| 463 extensions::WarningSet* conflicting_extensions, | 469 extensions::WarningSet* conflicting_extensions, |
| 464 const net::NetLogWithSource* net_log) { | 470 const net::NetLogWithSource* net_log) { |
| 465 // First handle only redirects to data:// URLs and about:blank. These are a | 471 // First handle only redirects to data:// URLs and about:blank. These are a |
| 466 // special case as they represent a way of cancelling a request. | 472 // special case as they represent a way of cancelling a request. |
| 467 if (MergeRedirectUrlOfResponsesHelper( | 473 if (MergeRedirectUrlOfResponsesHelper( |
| 468 deltas, new_url, conflicting_extensions, net_log, true)) { | 474 url, deltas, new_url, conflicting_extensions, net_log, true)) { |
| 469 // If any extension cancelled a request by redirecting to a data:// URL or | 475 // If any extension cancelled a request by redirecting to a data:// URL or |
| 470 // about:blank, we don't consider the other redirects. | 476 // about:blank, we don't consider the other redirects. |
| 471 return; | 477 return; |
| 472 } | 478 } |
| 473 | 479 |
| 474 // Handle all other redirects. | 480 // Handle all other redirects. |
| 475 MergeRedirectUrlOfResponsesHelper( | 481 MergeRedirectUrlOfResponsesHelper(url, deltas, new_url, |
| 476 deltas, new_url, conflicting_extensions, net_log, false); | 482 conflicting_extensions, net_log, false); |
| 477 } | 483 } |
| 478 | 484 |
| 479 void MergeOnBeforeRequestResponses( | 485 void MergeOnBeforeRequestResponses( |
| 486 const GURL& url, |
| 480 const EventResponseDeltas& deltas, | 487 const EventResponseDeltas& deltas, |
| 481 GURL* new_url, | 488 GURL* new_url, |
| 482 extensions::WarningSet* conflicting_extensions, | 489 extensions::WarningSet* conflicting_extensions, |
| 483 const net::NetLogWithSource* net_log) { | 490 const net::NetLogWithSource* net_log) { |
| 484 MergeRedirectUrlOfResponses(deltas, new_url, conflicting_extensions, net_log); | 491 MergeRedirectUrlOfResponses(url, deltas, new_url, conflicting_extensions, |
| 492 net_log); |
| 485 } | 493 } |
| 486 | 494 |
| 487 static bool DoesRequestCookieMatchFilter( | 495 static bool DoesRequestCookieMatchFilter( |
| 488 const ParsedRequestCookie& cookie, | 496 const ParsedRequestCookie& cookie, |
| 489 RequestCookie* filter) { | 497 RequestCookie* filter) { |
| 490 if (!filter) return true; | 498 if (!filter) return true; |
| 491 if (filter->name.get() && cookie.first != *filter->name) return false; | 499 if (filter->name.get() && cookie.first != *filter->name) return false; |
| 492 if (filter->value.get() && cookie.second != *filter->value) return false; | 500 if (filter->value.get() && cookie.second != *filter->value) return false; |
| 493 return true; | 501 return true; |
| 494 } | 502 } |
| (...skipping 535 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1030 for (const auto& delta : deltas) { | 1038 for (const auto& delta : deltas) { |
| 1031 for (const auto& deleted_hdr : delta->deleted_response_headers) { | 1039 for (const auto& deleted_hdr : delta->deleted_response_headers) { |
| 1032 if (base::ToLowerASCII(deleted_hdr.first) == lower_key) | 1040 if (base::ToLowerASCII(deleted_hdr.first) == lower_key) |
| 1033 return delta->extension_id; | 1041 return delta->extension_id; |
| 1034 } | 1042 } |
| 1035 } | 1043 } |
| 1036 return std::string(); | 1044 return std::string(); |
| 1037 } | 1045 } |
| 1038 | 1046 |
| 1039 void MergeOnHeadersReceivedResponses( | 1047 void MergeOnHeadersReceivedResponses( |
| 1048 const GURL& url, |
| 1040 const EventResponseDeltas& deltas, | 1049 const EventResponseDeltas& deltas, |
| 1041 const net::HttpResponseHeaders* original_response_headers, | 1050 const net::HttpResponseHeaders* original_response_headers, |
| 1042 scoped_refptr<net::HttpResponseHeaders>* override_response_headers, | 1051 scoped_refptr<net::HttpResponseHeaders>* override_response_headers, |
| 1043 GURL* allowed_unsafe_redirect_url, | 1052 GURL* allowed_unsafe_redirect_url, |
| 1044 extensions::WarningSet* conflicting_extensions, | 1053 extensions::WarningSet* conflicting_extensions, |
| 1045 const net::NetLogWithSource* net_log) { | 1054 const net::NetLogWithSource* net_log) { |
| 1046 EventResponseDeltas::const_iterator delta; | 1055 EventResponseDeltas::const_iterator delta; |
| 1047 | 1056 |
| 1048 // Here we collect which headers we have removed or added so far due to | 1057 // Here we collect which headers we have removed or added so far due to |
| 1049 // extensions of higher precedence. Header keys are always stored as | 1058 // extensions of higher precedence. Header keys are always stored as |
| (...skipping 66 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1116 net_log->AddEvent( | 1125 net_log->AddEvent( |
| 1117 net::NetLogEventType::CHROME_EXTENSION_IGNORED_DUE_TO_CONFLICT, | 1126 net::NetLogEventType::CHROME_EXTENSION_IGNORED_DUE_TO_CONFLICT, |
| 1118 CreateNetLogExtensionIdCallback(delta->get())); | 1127 CreateNetLogExtensionIdCallback(delta->get())); |
| 1119 } | 1128 } |
| 1120 } | 1129 } |
| 1121 | 1130 |
| 1122 MergeCookiesInOnHeadersReceivedResponses(deltas, original_response_headers, | 1131 MergeCookiesInOnHeadersReceivedResponses(deltas, original_response_headers, |
| 1123 override_response_headers, conflicting_extensions, net_log); | 1132 override_response_headers, conflicting_extensions, net_log); |
| 1124 | 1133 |
| 1125 GURL new_url; | 1134 GURL new_url; |
| 1126 MergeRedirectUrlOfResponses( | 1135 MergeRedirectUrlOfResponses(url, deltas, &new_url, conflicting_extensions, |
| 1127 deltas, &new_url, conflicting_extensions, net_log); | 1136 net_log); |
| 1128 if (new_url.is_valid()) { | 1137 if (new_url.is_valid()) { |
| 1129 // Only create a copy if we really want to modify the response headers. | 1138 // Only create a copy if we really want to modify the response headers. |
| 1130 if (override_response_headers->get() == NULL) { | 1139 if (override_response_headers->get() == NULL) { |
| 1131 *override_response_headers = new net::HttpResponseHeaders( | 1140 *override_response_headers = new net::HttpResponseHeaders( |
| 1132 original_response_headers->raw_headers()); | 1141 original_response_headers->raw_headers()); |
| 1133 } | 1142 } |
| 1134 (*override_response_headers)->ReplaceStatusLine("HTTP/1.1 302 Found"); | 1143 (*override_response_headers)->ReplaceStatusLine("HTTP/1.1 302 Found"); |
| 1135 (*override_response_headers)->RemoveHeader("location"); | 1144 (*override_response_headers)->RemoveHeader("location"); |
| 1136 (*override_response_headers)->AddHeader("Location: " + new_url.spec()); | 1145 (*override_response_headers)->AddHeader("Location: " + new_url.spec()); |
| 1137 // Explicitly mark the URL as safe for redirection, to prevent the request | 1146 // Explicitly mark the URL as safe for redirection, to prevent the request |
| (...skipping 58 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1196 if (base::IsStringUTF8(value)) { | 1205 if (base::IsStringUTF8(value)) { |
| 1197 header->SetString(keys::kHeaderValueKey, value); | 1206 header->SetString(keys::kHeaderValueKey, value); |
| 1198 } else { | 1207 } else { |
| 1199 header->Set(keys::kHeaderBinaryValueKey, | 1208 header->Set(keys::kHeaderBinaryValueKey, |
| 1200 StringToCharList(value)); | 1209 StringToCharList(value)); |
| 1201 } | 1210 } |
| 1202 return header; | 1211 return header; |
| 1203 } | 1212 } |
| 1204 | 1213 |
| 1205 } // namespace extension_web_request_api_helpers | 1214 } // namespace extension_web_request_api_helpers |
| OLD | NEW |