fetch redirect is incompatible with "no-cors" mode
https://bugs.webkit.org/show_bug.cgi?id=181866
<rdar://problem/35827140>

Patch by Youenn Fablet <youenn@apple.com> on 2018-01-20
Reviewed by Chris Dumez.

LayoutTests/imported/w3c:

* web-platform-tests/fetch/api/redirect/redirect-mode-expected.txt:
* web-platform-tests/fetch/api/redirect/redirect-mode-worker-expected.txt:
* web-platform-tests/fetch/api/redirect/redirect-mode.js:
(redirectMode):
* web-platform-tests/service-workers/service-worker/fetch-event-redirect.https-expected.txt:
* web-platform-tests/service-workers/service-worker/fetch-event-redirect.https.html:
* web-platform-tests/service-workers/service-worker/fetch-request-redirect.https-expected.txt:

Source/WebCore:

Covered by updated tests.

Return a network error when no-cors mode and redirect mode is manual or error.
Update preflight implementation to no longer use manual redirect mode to simulate https://fetch.spec.whatwg.org/#http-network-or-cache-fetch.
Instead implement redirectReceived callback to treat any redirect response as the preflight response.

* loader/cache/CachedResourceLoader.cpp:
(WebCore::CachedResourceLoader::canRequest):
* loader/CrossOriginPreflightChecker.cpp:
(WebCore::CrossOriginPreflightChecker::redirectReceived):
(WebCore::CrossOriginPreflightChecker::startPreflight):
* loader/CrossOriginPreflightChecker.h:

LayoutTests:

* http/tests/fetch/redirectmode-and-preload-expected.txt:
* http/tests/fetch/redirectmode-and-preload.html:

git-svn-id: http://svn.webkit.org/repository/webkit/trunk@227270 268f45cc-cd09-0410-ab3c-d52691b4dbfc
diff --git a/Source/WebCore/loader/CrossOriginPreflightChecker.cpp b/Source/WebCore/loader/CrossOriginPreflightChecker.cpp
index 7d375fe..9aa9b61 100644
--- a/Source/WebCore/loader/CrossOriginPreflightChecker.cpp
+++ b/Source/WebCore/loader/CrossOriginPreflightChecker.cpp
@@ -95,11 +95,17 @@
     validatePreflightResponse(m_loader, WTFMove(m_request), m_resource->identifier(), m_resource->response());
 }
 
+void CrossOriginPreflightChecker::redirectReceived(CachedResource& resource, ResourceRequest&&, const ResourceResponse& response, CompletionHandler<void(ResourceRequest&&)>&& completionHandler)
+{
+    ASSERT_UNUSED(resource, &resource == m_resource);
+    validatePreflightResponse(m_loader, WTFMove(m_request), m_resource->identifier(), response);
+    completionHandler(ResourceRequest { });
+}
+
 void CrossOriginPreflightChecker::startPreflight()
 {
     ResourceLoaderOptions options;
     options.referrerPolicy = m_loader.options().referrerPolicy;
-    options.redirect = FetchOptions::Redirect::Manual;
     options.contentSecurityPolicyImposition = ContentSecurityPolicyImposition::SkipPolicyCheck;
     options.serviceWorkersMode = ServiceWorkersMode::None;