TestController should clear all fetch caches when resetting its state
[WebKit-https.git] / Tools / WebKitTestRunner / TestInvocation.cpp
1 /*
2  * Copyright (C) 2010-2017 Apple Inc. All rights reserved.
3  * Copyright (C) 2012 Intel Corporation. All rights reserved.
4  *
5  * Redistribution and use in source and binary forms, with or without
6  * modification, are permitted provided that the following conditions
7  * are met:
8  * 1. Redistributions of source code must retain the above copyright
9  *    notice, this list of conditions and the following disclaimer.
10  * 2. Redistributions in binary form must reproduce the above copyright
11  *    notice, this list of conditions and the following disclaimer in the
12  *    documentation and/or other materials provided with the distribution.
13  *
14  * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
15  * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
16  * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
17  * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
18  * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19  * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20  * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21  * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22  * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23  * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
24  * THE POSSIBILITY OF SUCH DAMAGE.
25  */
26
27 #include "config.h"
28 #include "TestInvocation.h"
29
30 #include "PlatformWebView.h"
31 #include "StringFunctions.h"
32 #include "TestController.h"
33 #include "UIScriptController.h"
34 #include "WebCoreTestSupport.h"
35 #include <WebKit/WKContextPrivate.h>
36 #include <WebKit/WKCookieManager.h>
37 #include <WebKit/WKData.h>
38 #include <WebKit/WKDictionary.h>
39 #include <WebKit/WKInspector.h>
40 #include <WebKit/WKPagePrivate.h>
41 #include <WebKit/WKRetainPtr.h>
42 #include <WebKit/WKWebsiteDataStoreRef.h>
43 #include <climits>
44 #include <cstdio>
45 #include <unistd.h>
46 #include <wtf/StdLibExtras.h>
47 #include <wtf/text/CString.h>
48
49 #if PLATFORM(MAC) && !PLATFORM(IOS)
50 #include <Carbon/Carbon.h>
51 #endif
52
53 #if PLATFORM(COCOA)
54 #include <WebKit/WKPagePrivateMac.h>
55 #endif
56
57 using namespace JSC;
58 using namespace WebKit;
59 using namespace std;
60
61 namespace WTR {
62
63 TestInvocation::TestInvocation(WKURLRef url, const TestOptions& options)
64     : m_options(options)
65     , m_url(url)
66 {
67     WKRetainPtr<WKStringRef> urlString = adoptWK(WKURLCopyString(m_url.get()));
68
69     size_t stringLength = WKStringGetLength(urlString.get());
70
71     Vector<char> urlVector;
72     urlVector.resize(stringLength + 1);
73
74     WKStringGetUTF8CString(urlString.get(), urlVector.data(), stringLength + 1);
75
76     m_urlString = String(urlVector.data(), stringLength);
77 }
78
79 TestInvocation::~TestInvocation()
80 {
81     if (m_pendingUIScriptInvocationData)
82         m_pendingUIScriptInvocationData->testInvocation = nullptr;
83 }
84
85 WKURLRef TestInvocation::url() const
86 {
87     return m_url.get();
88 }
89
90 bool TestInvocation::urlContains(const char* searchString) const
91 {
92     return m_urlString.contains(searchString, false);
93 }
94
95 void TestInvocation::setIsPixelTest(const std::string& expectedPixelHash)
96 {
97     m_dumpPixels = true;
98     m_expectedPixelHash = expectedPixelHash;
99 }
100
101 double TestInvocation::shortTimeout() const
102 {
103     if (!m_timeout) {
104         // Running WKTR directly, without webkitpy.
105         return TestController::defaultShortTimeout;
106     }
107
108     // This is not exactly correct for the way short timeout is used - it should not depend on whether a test is "slow",
109     // but it currently does. There is no way to know what a normal test's timeout is, as webkitpy only passes timeouts
110     // for each test individually.
111     // But there shouldn't be any observable negative consequences from this.
112     return m_timeout / 1000. / 2;
113 }
114
115 bool TestInvocation::shouldLogFrameLoadDelegates() const
116 {
117     return urlContains("loading/");
118 }
119
120 bool TestInvocation::shouldLogHistoryClientCallbacks() const
121 {
122     return urlContains("globalhistory/");
123 }
124
125 void TestInvocation::invoke()
126 {
127     TestController::singleton().configureViewForTest(*this);
128
129     WKPageSetAddsVisitedLinks(TestController::singleton().mainWebView()->page(), false);
130
131     m_textOutput.clear();
132
133     TestController::singleton().setShouldLogHistoryClientCallbacks(shouldLogHistoryClientCallbacks());
134
135     WKCookieManagerSetHTTPCookieAcceptPolicy(WKContextGetCookieManager(TestController::singleton().context()), kWKHTTPCookieAcceptPolicyOnlyFromMainDocumentDomain);
136
137     // FIXME: We should clear out visited links here.
138
139     WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("BeginTest"));
140     WKRetainPtr<WKMutableDictionaryRef> beginTestMessageBody = adoptWK(WKMutableDictionaryCreate());
141
142     WKRetainPtr<WKStringRef> dumpFrameLoadDelegatesKey = adoptWK(WKStringCreateWithUTF8CString("DumpFrameLoadDelegates"));
143     WKRetainPtr<WKBooleanRef> dumpFrameLoadDelegatesValue = adoptWK(WKBooleanCreate(shouldLogFrameLoadDelegates()));
144     WKDictionarySetItem(beginTestMessageBody.get(), dumpFrameLoadDelegatesKey.get(), dumpFrameLoadDelegatesValue.get());
145
146     WKRetainPtr<WKStringRef> useFlexibleViewportKey = adoptWK(WKStringCreateWithUTF8CString("UseFlexibleViewport"));
147     WKRetainPtr<WKBooleanRef> useFlexibleViewportValue = adoptWK(WKBooleanCreate(options().useFlexibleViewport));
148     WKDictionarySetItem(beginTestMessageBody.get(), useFlexibleViewportKey.get(), useFlexibleViewportValue.get());
149
150     WKRetainPtr<WKStringRef> dumpPixelsKey = adoptWK(WKStringCreateWithUTF8CString("DumpPixels"));
151     WKRetainPtr<WKBooleanRef> dumpPixelsValue = adoptWK(WKBooleanCreate(m_dumpPixels));
152     WKDictionarySetItem(beginTestMessageBody.get(), dumpPixelsKey.get(), dumpPixelsValue.get());
153
154     WKRetainPtr<WKStringRef> useWaitToDumpWatchdogTimerKey = adoptWK(WKStringCreateWithUTF8CString("UseWaitToDumpWatchdogTimer"));
155     WKRetainPtr<WKBooleanRef> useWaitToDumpWatchdogTimerValue = adoptWK(WKBooleanCreate(TestController::singleton().useWaitToDumpWatchdogTimer()));
156     WKDictionarySetItem(beginTestMessageBody.get(), useWaitToDumpWatchdogTimerKey.get(), useWaitToDumpWatchdogTimerValue.get());
157
158     WKRetainPtr<WKStringRef> timeoutKey = adoptWK(WKStringCreateWithUTF8CString("Timeout"));
159     WKRetainPtr<WKUInt64Ref> timeoutValue = adoptWK(WKUInt64Create(m_timeout));
160     WKDictionarySetItem(beginTestMessageBody.get(), timeoutKey.get(), timeoutValue.get());
161
162     WKRetainPtr<WKStringRef> dumpJSConsoleLogInStdErrKey = adoptWK(WKStringCreateWithUTF8CString("DumpJSConsoleLogInStdErr"));
163     WKRetainPtr<WKBooleanRef> dumpJSConsoleLogInStdErrValue = adoptWK(WKBooleanCreate(m_dumpJSConsoleLogInStdErr));
164     WKDictionarySetItem(beginTestMessageBody.get(), dumpJSConsoleLogInStdErrKey.get(), dumpJSConsoleLogInStdErrValue.get());
165
166     WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), beginTestMessageBody.get());
167
168     bool shouldOpenExternalURLs = false;
169
170     TestController::singleton().runUntil(m_gotInitialResponse, shortTimeout());
171     if (!m_gotInitialResponse) {
172         m_errorMessage = "Timed out waiting for initial response from web process\n";
173         m_webProcessIsUnresponsive = true;
174         goto end;
175     }
176     if (m_error)
177         goto end;
178
179     WKPageLoadURLWithShouldOpenExternalURLsPolicy(TestController::singleton().mainWebView()->page(), m_url.get(), shouldOpenExternalURLs);
180
181     TestController::singleton().runUntil(m_gotFinalMessage, TestController::noTimeout);
182     if (m_error)
183         goto end;
184
185     dumpResults();
186
187 end:
188 #if !PLATFORM(IOS)
189     if (m_gotInitialResponse)
190         WKInspectorClose(WKPageGetInspector(TestController::singleton().mainWebView()->page()));
191 #endif // !PLATFORM(IOS)
192
193     if (m_webProcessIsUnresponsive)
194         dumpWebProcessUnresponsiveness();
195     else if (TestController::singleton().resetStateToConsistentValues(m_options))
196         return;
197
198     // The process is unresponsive, so let's start a new one.
199     TestController::singleton().terminateWebContentProcess();
200     // Make sure that we have a process, as invoke() will need one to send bundle messages for the next test.
201     TestController::singleton().reattachPageToWebProcess();
202 }
203
204 void TestInvocation::dumpWebProcessUnresponsiveness()
205 {
206     dumpWebProcessUnresponsiveness(m_errorMessage.c_str());
207 }
208
209 void TestInvocation::dumpWebProcessUnresponsiveness(const char* errorMessage)
210 {
211     fprintf(stderr, "%s", errorMessage);
212     char buffer[1024] = { };
213 #if PLATFORM(COCOA)
214     pid_t pid = WKPageGetProcessIdentifier(TestController::singleton().mainWebView()->page());
215     snprintf(buffer, sizeof(buffer), "#PROCESS UNRESPONSIVE - %s (pid %ld)\n", TestController::webProcessName(), static_cast<long>(pid));
216 #else
217     snprintf(buffer, sizeof(buffer), "#PROCESS UNRESPONSIVE - %s\n", TestController::webProcessName());
218 #endif
219
220     dump(errorMessage, buffer, true);
221     
222     if (!TestController::singleton().usingServerMode())
223         return;
224     
225     if (isatty(fileno(stdin)) || isatty(fileno(stderr)))
226         fputs("Grab an image of the stack, then hit enter...\n", stderr);
227     
228     if (!fgets(buffer, sizeof(buffer), stdin) || strcmp(buffer, "#SAMPLE FINISHED\n"))
229         fprintf(stderr, "Failed receive expected sample response, got:\n\t\"%s\"\nContinuing...\n", buffer);
230 }
231
232 void TestInvocation::dump(const char* textToStdout, const char* textToStderr, bool seenError)
233 {
234     printf("Content-Type: text/plain\n");
235     if (textToStdout)
236         fputs(textToStdout, stdout);
237     if (textToStderr)
238         fputs(textToStderr, stderr);
239
240     fputs("#EOF\n", stdout);
241     fputs("#EOF\n", stderr);
242     if (seenError)
243         fputs("#EOF\n", stdout);
244     fflush(stdout);
245     fflush(stderr);
246 }
247
248 void TestInvocation::forceRepaintDoneCallback(WKErrorRef error, void* context)
249 {
250     // The context may not be valid any more, e.g. if WebKit is invalidating callbacks at process exit.
251     if (error)
252         return;
253
254     TestInvocation* testInvocation = static_cast<TestInvocation*>(context);
255     RELEASE_ASSERT(TestController::singleton().isCurrentInvocation(testInvocation));
256
257     testInvocation->m_gotRepaint = true;
258     TestController::singleton().notifyDone();
259 }
260
261 void TestInvocation::dumpResults()
262 {
263     if (m_textOutput.length() || !m_audioResult)
264         dump(m_textOutput.toString().utf8().data());
265     else
266         dumpAudio(m_audioResult.get());
267
268     if (m_dumpPixels) {
269         if (m_pixelResult)
270             dumpPixelsAndCompareWithExpected(SnapshotResultType::WebContents, m_repaintRects.get(), m_pixelResult.get());
271         else if (m_pixelResultIsPending) {
272             m_gotRepaint = false;
273             WKPageForceRepaint(TestController::singleton().mainWebView()->page(), this, TestInvocation::forceRepaintDoneCallback);
274             TestController::singleton().runUntil(m_gotRepaint, shortTimeout());
275             if (!m_gotRepaint) {
276                 m_errorMessage = "Timed out waiting for pre-pixel dump repaint\n";
277                 m_webProcessIsUnresponsive = true;
278                 return;
279             }
280
281             dumpPixelsAndCompareWithExpected(SnapshotResultType::WebView, m_repaintRects.get());
282         }
283     }
284
285     fputs("#EOF\n", stdout);
286     fflush(stdout);
287     fflush(stderr);
288 }
289
290 void TestInvocation::dumpAudio(WKDataRef audioData)
291 {
292     size_t length = WKDataGetSize(audioData);
293     if (!length)
294         return;
295
296     const unsigned char* data = WKDataGetBytes(audioData);
297
298     printf("Content-Type: audio/wav\n");
299     printf("Content-Length: %lu\n", static_cast<unsigned long>(length));
300
301     fwrite(data, 1, length, stdout);
302     printf("#EOF\n");
303     fprintf(stderr, "#EOF\n");
304 }
305
306 bool TestInvocation::compareActualHashToExpectedAndDumpResults(const char actualHash[33])
307 {
308     // Compute the hash of the bitmap context pixels
309     fprintf(stdout, "\nActualHash: %s\n", actualHash);
310
311     if (!m_expectedPixelHash.length())
312         return false;
313
314     ASSERT(m_expectedPixelHash.length() == 32);
315     fprintf(stdout, "\nExpectedHash: %s\n", m_expectedPixelHash.c_str());
316
317     // FIXME: Do case insensitive compare.
318     return m_expectedPixelHash == actualHash;
319 }
320
321 void TestInvocation::didReceiveMessageFromInjectedBundle(WKStringRef messageName, WKTypeRef messageBody)
322 {
323     if (WKStringIsEqualToUTF8CString(messageName, "Error")) {
324         // Set all states to true to stop spinning the runloop.
325         m_gotInitialResponse = true;
326         m_gotFinalMessage = true;
327         m_error = true;
328         m_errorMessage = "FAIL\n";
329         TestController::singleton().notifyDone();
330         return;
331     }
332
333     if (WKStringIsEqualToUTF8CString(messageName, "Ack")) {
334         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
335         WKStringRef messageBodyString = static_cast<WKStringRef>(messageBody);
336         if (WKStringIsEqualToUTF8CString(messageBodyString, "BeginTest")) {
337             m_gotInitialResponse = true;
338             TestController::singleton().notifyDone();
339             return;
340         }
341
342         ASSERT_NOT_REACHED();
343     }
344
345     if (WKStringIsEqualToUTF8CString(messageName, "Done")) {
346         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
347         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
348
349         WKRetainPtr<WKStringRef> pixelResultIsPendingKey = adoptWK(WKStringCreateWithUTF8CString("PixelResultIsPending"));
350         WKBooleanRef pixelResultIsPending = static_cast<WKBooleanRef>(WKDictionaryGetItemForKey(messageBodyDictionary, pixelResultIsPendingKey.get()));
351         m_pixelResultIsPending = WKBooleanGetValue(pixelResultIsPending);
352
353         if (!m_pixelResultIsPending) {
354             WKRetainPtr<WKStringRef> pixelResultKey = adoptWK(WKStringCreateWithUTF8CString("PixelResult"));
355             m_pixelResult = static_cast<WKImageRef>(WKDictionaryGetItemForKey(messageBodyDictionary, pixelResultKey.get()));
356             ASSERT(!m_pixelResult || m_dumpPixels);
357         }
358
359         WKRetainPtr<WKStringRef> repaintRectsKey = adoptWK(WKStringCreateWithUTF8CString("RepaintRects"));
360         m_repaintRects = static_cast<WKArrayRef>(WKDictionaryGetItemForKey(messageBodyDictionary, repaintRectsKey.get()));
361
362         WKRetainPtr<WKStringRef> audioResultKey =  adoptWK(WKStringCreateWithUTF8CString("AudioResult"));
363         m_audioResult = static_cast<WKDataRef>(WKDictionaryGetItemForKey(messageBodyDictionary, audioResultKey.get()));
364
365         m_gotFinalMessage = true;
366         TestController::singleton().notifyDone();
367         return;
368     }
369
370     if (WKStringIsEqualToUTF8CString(messageName, "TextOutput")) {
371         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
372         WKStringRef textOutput = static_cast<WKStringRef>(messageBody);
373         m_textOutput.append(toWTFString(textOutput));
374         return;
375     }
376
377     if (WKStringIsEqualToUTF8CString(messageName, "DumpToStdErr")) {
378         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
379         WKStringRef textOutput = static_cast<WKStringRef>(messageBody);
380         fprintf(stderr, "%s", toWTFString(textOutput).utf8().data());
381         return;
382     }
383
384     if (WKStringIsEqualToUTF8CString(messageName, "BeforeUnloadReturnValue")) {
385         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
386         WKBooleanRef beforeUnloadReturnValue = static_cast<WKBooleanRef>(messageBody);
387         TestController::singleton().setBeforeUnloadReturnValue(WKBooleanGetValue(beforeUnloadReturnValue));
388         return;
389     }
390     
391     if (WKStringIsEqualToUTF8CString(messageName, "AddChromeInputField")) {
392         TestController::singleton().mainWebView()->addChromeInputField();
393         WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("CallAddChromeInputFieldCallback"));
394         WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
395         return;
396     }
397
398     if (WKStringIsEqualToUTF8CString(messageName, "RemoveChromeInputField")) {
399         TestController::singleton().mainWebView()->removeChromeInputField();
400         WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("CallRemoveChromeInputFieldCallback"));
401         WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
402         return;
403     }
404     
405     if (WKStringIsEqualToUTF8CString(messageName, "FocusWebView")) {
406         TestController::singleton().mainWebView()->makeWebViewFirstResponder();
407         WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("CallFocusWebViewCallback"));
408         WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
409         return;
410     }
411
412     if (WKStringIsEqualToUTF8CString(messageName, "SetBackingScaleFactor")) {
413         ASSERT(WKGetTypeID(messageBody) == WKDoubleGetTypeID());
414         double backingScaleFactor = WKDoubleGetValue(static_cast<WKDoubleRef>(messageBody));
415         WKPageSetCustomBackingScaleFactor(TestController::singleton().mainWebView()->page(), backingScaleFactor);
416
417         WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("CallSetBackingScaleFactorCallback"));
418         WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
419         return;
420     }
421
422     if (WKStringIsEqualToUTF8CString(messageName, "SimulateWebNotificationClick")) {
423         ASSERT(WKGetTypeID(messageBody) == WKUInt64GetTypeID());
424         uint64_t notificationID = WKUInt64GetValue(static_cast<WKUInt64Ref>(messageBody));
425         TestController::singleton().simulateWebNotificationClick(notificationID);
426         return;
427     }
428
429     if (WKStringIsEqualToUTF8CString(messageName, "SetAddsVisitedLinks")) {
430         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
431         WKBooleanRef enabledWK = static_cast<WKBooleanRef>(messageBody);
432         WKPageSetAddsVisitedLinks(TestController::singleton().mainWebView()->page(), WKBooleanGetValue(enabledWK));
433         return;
434     }
435
436     if (WKStringIsEqualToUTF8CString(messageName, "SetGeolocationPermission")) {
437         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
438         WKBooleanRef enabledWK = static_cast<WKBooleanRef>(messageBody);
439         TestController::singleton().setGeolocationPermission(WKBooleanGetValue(enabledWK));
440         return;
441     }
442
443     if (WKStringIsEqualToUTF8CString(messageName, "SetMockGeolocationPosition")) {
444         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
445         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
446
447         WKRetainPtr<WKStringRef> latitudeKeyWK(AdoptWK, WKStringCreateWithUTF8CString("latitude"));
448         WKDoubleRef latitudeWK = static_cast<WKDoubleRef>(WKDictionaryGetItemForKey(messageBodyDictionary, latitudeKeyWK.get()));
449         double latitude = WKDoubleGetValue(latitudeWK);
450
451         WKRetainPtr<WKStringRef> longitudeKeyWK(AdoptWK, WKStringCreateWithUTF8CString("longitude"));
452         WKDoubleRef longitudeWK = static_cast<WKDoubleRef>(WKDictionaryGetItemForKey(messageBodyDictionary, longitudeKeyWK.get()));
453         double longitude = WKDoubleGetValue(longitudeWK);
454
455         WKRetainPtr<WKStringRef> accuracyKeyWK(AdoptWK, WKStringCreateWithUTF8CString("accuracy"));
456         WKDoubleRef accuracyWK = static_cast<WKDoubleRef>(WKDictionaryGetItemForKey(messageBodyDictionary, accuracyKeyWK.get()));
457         double accuracy = WKDoubleGetValue(accuracyWK);
458
459         WKRetainPtr<WKStringRef> providesAltitudeKeyWK(AdoptWK, WKStringCreateWithUTF8CString("providesAltitude"));
460         WKBooleanRef providesAltitudeWK = static_cast<WKBooleanRef>(WKDictionaryGetItemForKey(messageBodyDictionary, providesAltitudeKeyWK.get()));
461         bool providesAltitude = WKBooleanGetValue(providesAltitudeWK);
462
463         WKRetainPtr<WKStringRef> altitudeKeyWK(AdoptWK, WKStringCreateWithUTF8CString("altitude"));
464         WKDoubleRef altitudeWK = static_cast<WKDoubleRef>(WKDictionaryGetItemForKey(messageBodyDictionary, altitudeKeyWK.get()));
465         double altitude = WKDoubleGetValue(altitudeWK);
466
467         WKRetainPtr<WKStringRef> providesAltitudeAccuracyKeyWK(AdoptWK, WKStringCreateWithUTF8CString("providesAltitudeAccuracy"));
468         WKBooleanRef providesAltitudeAccuracyWK = static_cast<WKBooleanRef>(WKDictionaryGetItemForKey(messageBodyDictionary, providesAltitudeAccuracyKeyWK.get()));
469         bool providesAltitudeAccuracy = WKBooleanGetValue(providesAltitudeAccuracyWK);
470
471         WKRetainPtr<WKStringRef> altitudeAccuracyKeyWK(AdoptWK, WKStringCreateWithUTF8CString("altitudeAccuracy"));
472         WKDoubleRef altitudeAccuracyWK = static_cast<WKDoubleRef>(WKDictionaryGetItemForKey(messageBodyDictionary, altitudeAccuracyKeyWK.get()));
473         double altitudeAccuracy = WKDoubleGetValue(altitudeAccuracyWK);
474
475         WKRetainPtr<WKStringRef> providesHeadingKeyWK(AdoptWK, WKStringCreateWithUTF8CString("providesHeading"));
476         WKBooleanRef providesHeadingWK = static_cast<WKBooleanRef>(WKDictionaryGetItemForKey(messageBodyDictionary, providesHeadingKeyWK.get()));
477         bool providesHeading = WKBooleanGetValue(providesHeadingWK);
478
479         WKRetainPtr<WKStringRef> headingKeyWK(AdoptWK, WKStringCreateWithUTF8CString("heading"));
480         WKDoubleRef headingWK = static_cast<WKDoubleRef>(WKDictionaryGetItemForKey(messageBodyDictionary, headingKeyWK.get()));
481         double heading = WKDoubleGetValue(headingWK);
482
483         WKRetainPtr<WKStringRef> providesSpeedKeyWK(AdoptWK, WKStringCreateWithUTF8CString("providesSpeed"));
484         WKBooleanRef providesSpeedWK = static_cast<WKBooleanRef>(WKDictionaryGetItemForKey(messageBodyDictionary, providesSpeedKeyWK.get()));
485         bool providesSpeed = WKBooleanGetValue(providesSpeedWK);
486
487         WKRetainPtr<WKStringRef> speedKeyWK(AdoptWK, WKStringCreateWithUTF8CString("speed"));
488         WKDoubleRef speedWK = static_cast<WKDoubleRef>(WKDictionaryGetItemForKey(messageBodyDictionary, speedKeyWK.get()));
489         double speed = WKDoubleGetValue(speedWK);
490
491         WKRetainPtr<WKStringRef> providesFloorLevelKeyWK(AdoptWK, WKStringCreateWithUTF8CString("providesFloorLevel"));
492         WKBooleanRef providesFloorLevelWK = static_cast<WKBooleanRef>(WKDictionaryGetItemForKey(messageBodyDictionary, providesFloorLevelKeyWK.get()));
493         bool providesFloorLevel = WKBooleanGetValue(providesFloorLevelWK);
494
495         WKRetainPtr<WKStringRef> floorLevelKeyWK(AdoptWK, WKStringCreateWithUTF8CString("floorLevel"));
496         WKDoubleRef floorLevelWK = static_cast<WKDoubleRef>(WKDictionaryGetItemForKey(messageBodyDictionary, floorLevelKeyWK.get()));
497         double floorLevel = WKDoubleGetValue(floorLevelWK);
498
499         TestController::singleton().setMockGeolocationPosition(latitude, longitude, accuracy, providesAltitude, altitude, providesAltitudeAccuracy, altitudeAccuracy, providesHeading, heading, providesSpeed, speed, providesFloorLevel, floorLevel);
500         return;
501     }
502
503     if (WKStringIsEqualToUTF8CString(messageName, "SetMockGeolocationPositionUnavailableError")) {
504         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
505         WKStringRef errorMessage = static_cast<WKStringRef>(messageBody);
506         TestController::singleton().setMockGeolocationPositionUnavailableError(errorMessage);
507         return;
508     }
509
510     if (WKStringIsEqualToUTF8CString(messageName, "SetUserMediaPermission")) {
511         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
512         WKBooleanRef enabledWK = static_cast<WKBooleanRef>(messageBody);
513         TestController::singleton().setUserMediaPermission(WKBooleanGetValue(enabledWK));
514         return;
515     }
516
517     if (WKStringIsEqualToUTF8CString(messageName, "ResetUserMediaPermission")) {
518         TestController::singleton().resetUserMediaPermission();
519         return;
520     }
521
522     if (WKStringIsEqualToUTF8CString(messageName, "SetUserMediaPersistentPermissionForOrigin")) {
523         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
524         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
525
526         WKRetainPtr<WKStringRef> permissionKeyWK(AdoptWK, WKStringCreateWithUTF8CString("permission"));
527         WKBooleanRef permissionWK = static_cast<WKBooleanRef>(WKDictionaryGetItemForKey(messageBodyDictionary, permissionKeyWK.get()));
528         bool permission = WKBooleanGetValue(permissionWK);
529
530         WKRetainPtr<WKStringRef> originKey(AdoptWK, WKStringCreateWithUTF8CString("origin"));
531         WKStringRef originWK = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, originKey.get()));
532
533         WKRetainPtr<WKStringRef> parentOriginKey(AdoptWK, WKStringCreateWithUTF8CString("parentOrigin"));
534         WKStringRef parentOriginWK = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, parentOriginKey.get()));
535
536         TestController::singleton().setUserMediaPersistentPermissionForOrigin(permission, originWK, parentOriginWK);
537         return;
538     }
539
540     if (WKStringIsEqualToUTF8CString(messageName, "ResetUserMediaPermissionRequestCountForOrigin")) {
541         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
542         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
543
544         WKRetainPtr<WKStringRef> originKey(AdoptWK, WKStringCreateWithUTF8CString("origin"));
545         WKStringRef originWK = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, originKey.get()));
546
547         WKRetainPtr<WKStringRef> parentOriginKey(AdoptWK, WKStringCreateWithUTF8CString("parentOrigin"));
548         WKStringRef parentOriginWK = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, parentOriginKey.get()));
549         
550         TestController::singleton().resetUserMediaPermissionRequestCountForOrigin(originWK, parentOriginWK);
551         return;
552     }
553
554     if (WKStringIsEqualToUTF8CString(messageName, "SetCacheModel")) {
555         ASSERT(WKGetTypeID(messageBody) == WKUInt64GetTypeID());
556         uint64_t model = WKUInt64GetValue(static_cast<WKUInt64Ref>(messageBody));
557         WKContextSetCacheModel(TestController::singleton().context(), model);
558         return;
559     }
560
561     if (WKStringIsEqualToUTF8CString(messageName, "SetCustomPolicyDelegate")) {
562         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
563         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
564
565         WKRetainPtr<WKStringRef> enabledKeyWK(AdoptWK, WKStringCreateWithUTF8CString("enabled"));
566         WKBooleanRef enabledWK = static_cast<WKBooleanRef>(WKDictionaryGetItemForKey(messageBodyDictionary, enabledKeyWK.get()));
567         bool enabled = WKBooleanGetValue(enabledWK);
568
569         WKRetainPtr<WKStringRef> permissiveKeyWK(AdoptWK, WKStringCreateWithUTF8CString("permissive"));
570         WKBooleanRef permissiveWK = static_cast<WKBooleanRef>(WKDictionaryGetItemForKey(messageBodyDictionary, permissiveKeyWK.get()));
571         bool permissive = WKBooleanGetValue(permissiveWK);
572
573         TestController::singleton().setCustomPolicyDelegate(enabled, permissive);
574         return;
575     }
576
577     if (WKStringIsEqualToUTF8CString(messageName, "SetHidden")) {
578         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
579         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
580
581         WKRetainPtr<WKStringRef> isInitialKeyWK(AdoptWK, WKStringCreateWithUTF8CString("hidden"));
582         WKBooleanRef hiddenWK = static_cast<WKBooleanRef>(WKDictionaryGetItemForKey(messageBodyDictionary, isInitialKeyWK.get()));
583         bool hidden = WKBooleanGetValue(hiddenWK);
584
585         TestController::singleton().setHidden(hidden);
586         return;
587     }
588
589     if (WKStringIsEqualToUTF8CString(messageName, "ProcessWorkQueue")) {
590         if (TestController::singleton().workQueueManager().processWorkQueue()) {
591             WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("WorkQueueProcessedCallback"));
592             WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
593         }
594         return;
595     }
596
597     if (WKStringIsEqualToUTF8CString(messageName, "QueueBackNavigation")) {
598         ASSERT(WKGetTypeID(messageBody) == WKUInt64GetTypeID());
599         uint64_t stepCount = WKUInt64GetValue(static_cast<WKUInt64Ref>(messageBody));
600         TestController::singleton().workQueueManager().queueBackNavigation(stepCount);
601         return;
602     }
603
604     if (WKStringIsEqualToUTF8CString(messageName, "QueueForwardNavigation")) {
605         ASSERT(WKGetTypeID(messageBody) == WKUInt64GetTypeID());
606         uint64_t stepCount = WKUInt64GetValue(static_cast<WKUInt64Ref>(messageBody));
607         TestController::singleton().workQueueManager().queueForwardNavigation(stepCount);
608         return;
609     }
610
611     if (WKStringIsEqualToUTF8CString(messageName, "QueueLoad")) {
612         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
613         WKDictionaryRef loadDataDictionary = static_cast<WKDictionaryRef>(messageBody);
614
615         WKRetainPtr<WKStringRef> urlKey(AdoptWK, WKStringCreateWithUTF8CString("url"));
616         WKStringRef urlWK = static_cast<WKStringRef>(WKDictionaryGetItemForKey(loadDataDictionary, urlKey.get()));
617
618         WKRetainPtr<WKStringRef> targetKey(AdoptWK, WKStringCreateWithUTF8CString("target"));
619         WKStringRef targetWK = static_cast<WKStringRef>(WKDictionaryGetItemForKey(loadDataDictionary, targetKey.get()));
620
621         WKRetainPtr<WKStringRef> shouldOpenExternalURLsKey(AdoptWK, WKStringCreateWithUTF8CString("shouldOpenExternalURLs"));
622         WKBooleanRef shouldOpenExternalURLsValueWK = static_cast<WKBooleanRef>(WKDictionaryGetItemForKey(loadDataDictionary, shouldOpenExternalURLsKey.get()));
623
624         TestController::singleton().workQueueManager().queueLoad(toWTFString(urlWK), toWTFString(targetWK), WKBooleanGetValue(shouldOpenExternalURLsValueWK));
625         return;
626     }
627
628     if (WKStringIsEqualToUTF8CString(messageName, "QueueLoadHTMLString")) {
629         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
630         WKDictionaryRef loadDataDictionary = static_cast<WKDictionaryRef>(messageBody);
631
632         WKRetainPtr<WKStringRef> contentKey(AdoptWK, WKStringCreateWithUTF8CString("content"));
633         WKStringRef contentWK = static_cast<WKStringRef>(WKDictionaryGetItemForKey(loadDataDictionary, contentKey.get()));
634
635         WKRetainPtr<WKStringRef> baseURLKey(AdoptWK, WKStringCreateWithUTF8CString("baseURL"));
636         WKStringRef baseURLWK = static_cast<WKStringRef>(WKDictionaryGetItemForKey(loadDataDictionary, baseURLKey.get()));
637
638         WKRetainPtr<WKStringRef> unreachableURLKey(AdoptWK, WKStringCreateWithUTF8CString("unreachableURL"));
639         WKStringRef unreachableURLWK = static_cast<WKStringRef>(WKDictionaryGetItemForKey(loadDataDictionary, unreachableURLKey.get()));
640
641         TestController::singleton().workQueueManager().queueLoadHTMLString(toWTFString(contentWK), baseURLWK ? toWTFString(baseURLWK) : String(), unreachableURLWK ? toWTFString(unreachableURLWK) : String());
642         return;
643     }
644
645     if (WKStringIsEqualToUTF8CString(messageName, "QueueReload")) {
646         TestController::singleton().workQueueManager().queueReload();
647         return;
648     }
649
650     if (WKStringIsEqualToUTF8CString(messageName, "QueueLoadingScript")) {
651         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
652         WKStringRef script = static_cast<WKStringRef>(messageBody);
653         TestController::singleton().workQueueManager().queueLoadingScript(toWTFString(script));
654         return;
655     }
656
657     if (WKStringIsEqualToUTF8CString(messageName, "QueueNonLoadingScript")) {
658         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
659         WKStringRef script = static_cast<WKStringRef>(messageBody);
660         TestController::singleton().workQueueManager().queueNonLoadingScript(toWTFString(script));
661         return;
662     }
663
664     if (WKStringIsEqualToUTF8CString(messageName, "SetRejectsProtectionSpaceAndContinueForAuthenticationChallenges")) {
665         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
666         WKBooleanRef value = static_cast<WKBooleanRef>(messageBody);
667         TestController::singleton().setRejectsProtectionSpaceAndContinueForAuthenticationChallenges(WKBooleanGetValue(value));
668         return;
669     }
670
671     if (WKStringIsEqualToUTF8CString(messageName, "SetHandlesAuthenticationChallenges")) {
672         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
673         WKBooleanRef value = static_cast<WKBooleanRef>(messageBody);
674         TestController::singleton().setHandlesAuthenticationChallenges(WKBooleanGetValue(value));
675         return;
676     }
677
678     if (WKStringIsEqualToUTF8CString(messageName, "SetShouldLogCanAuthenticateAgainstProtectionSpace")) {
679         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
680         WKBooleanRef value = static_cast<WKBooleanRef>(messageBody);
681         TestController::singleton().setShouldLogCanAuthenticateAgainstProtectionSpace(WKBooleanGetValue(value));
682         return;
683     }
684
685     if (WKStringIsEqualToUTF8CString(messageName, "SetShouldLogDownloadCallbacks")) {
686         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
687         WKBooleanRef value = static_cast<WKBooleanRef>(messageBody);
688         TestController::singleton().setShouldLogDownloadCallbacks(WKBooleanGetValue(value));
689         return;
690     }
691
692     if (WKStringIsEqualToUTF8CString(messageName, "SetAuthenticationUsername")) {
693         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
694         WKStringRef username = static_cast<WKStringRef>(messageBody);
695         TestController::singleton().setAuthenticationUsername(toWTFString(username));
696         return;
697     }
698
699     if (WKStringIsEqualToUTF8CString(messageName, "SetAuthenticationPassword")) {
700         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
701         WKStringRef password = static_cast<WKStringRef>(messageBody);
702         TestController::singleton().setAuthenticationPassword(toWTFString(password));
703         return;
704     }
705
706     if (WKStringIsEqualToUTF8CString(messageName, "SetBlockAllPlugins")) {
707         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
708         WKBooleanRef shouldBlock = static_cast<WKBooleanRef>(messageBody);
709         TestController::singleton().setBlockAllPlugins(WKBooleanGetValue(shouldBlock));
710         return;
711     }
712
713     if (WKStringIsEqualToUTF8CString(messageName, "SetShouldDecideNavigationPolicyAfterDelay")) {
714         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
715         WKBooleanRef value = static_cast<WKBooleanRef>(messageBody);
716         TestController::singleton().setShouldDecideNavigationPolicyAfterDelay(WKBooleanGetValue(value));
717         return;
718     }
719
720     if (WKStringIsEqualToUTF8CString(messageName, "SetNavigationGesturesEnabled")) {
721         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
722         WKBooleanRef value = static_cast<WKBooleanRef>(messageBody);
723         TestController::singleton().setNavigationGesturesEnabled(WKBooleanGetValue(value));
724         return;
725     }
726     
727     if (WKStringIsEqualToUTF8CString(messageName, "SetIgnoresViewportScaleLimits")) {
728         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
729         WKBooleanRef value = static_cast<WKBooleanRef>(messageBody);
730         TestController::singleton().setIgnoresViewportScaleLimits(WKBooleanGetValue(value));
731         return;
732     }
733
734     if (WKStringIsEqualToUTF8CString(messageName, "SetShouldDownloadUndisplayableMIMETypes")) {
735         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
736         WKBooleanRef value = static_cast<WKBooleanRef>(messageBody);
737         TestController::singleton().setShouldDownloadUndisplayableMIMETypes(WKBooleanGetValue(value));
738         return;
739     }
740
741     if (WKStringIsEqualToUTF8CString(messageName, "TerminateNetworkProcess")) {
742         ASSERT(!messageBody);
743         TestController::singleton().terminateNetworkProcess();
744         return;
745     }
746
747     if (WKStringIsEqualToUTF8CString(messageName, "RunUIProcessScript")) {
748         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
749         WKRetainPtr<WKStringRef> scriptKey(AdoptWK, WKStringCreateWithUTF8CString("Script"));
750         WKRetainPtr<WKStringRef> callbackIDKey(AdoptWK, WKStringCreateWithUTF8CString("CallbackID"));
751
752         UIScriptInvocationData* invocationData = new UIScriptInvocationData();
753         invocationData->testInvocation = this;
754         invocationData->callbackID = (unsigned)WKUInt64GetValue(static_cast<WKUInt64Ref>(WKDictionaryGetItemForKey(messageBodyDictionary, callbackIDKey.get())));
755         invocationData->scriptString = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, scriptKey.get()));
756         m_pendingUIScriptInvocationData = invocationData;
757         WKPageCallAfterNextPresentationUpdate(TestController::singleton().mainWebView()->page(), invocationData, runUISideScriptAfterUpdateCallback);
758         return;
759     }
760
761     if (WKStringIsEqualToUTF8CString(messageName, "SetOpenPanelFileURLs")) {
762         TestController::singleton().setOpenPanelFileURLs(static_cast<WKArrayRef>(messageBody));
763         return;
764     }
765
766     ASSERT_NOT_REACHED();
767 }
768
769 WKRetainPtr<WKTypeRef> TestInvocation::didReceiveSynchronousMessageFromInjectedBundle(WKStringRef messageName, WKTypeRef messageBody)
770 {
771     if (WKStringIsEqualToUTF8CString(messageName, "SetWindowIsKey")) {
772         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
773         WKBooleanRef isKeyValue = static_cast<WKBooleanRef>(messageBody);
774         TestController::singleton().mainWebView()->setWindowIsKey(WKBooleanGetValue(isKeyValue));
775         return nullptr;
776     }
777
778     if (WKStringIsEqualToUTF8CString(messageName, "SetViewSize")) {
779         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
780
781         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
782         WKRetainPtr<WKStringRef> widthKey(AdoptWK, WKStringCreateWithUTF8CString("width"));
783         WKRetainPtr<WKStringRef> heightKey(AdoptWK, WKStringCreateWithUTF8CString("height"));
784
785         WKDoubleRef widthWK = static_cast<WKDoubleRef>(WKDictionaryGetItemForKey(messageBodyDictionary, widthKey.get()));
786         WKDoubleRef heightWK = static_cast<WKDoubleRef>(WKDictionaryGetItemForKey(messageBodyDictionary, heightKey.get()));
787
788         TestController::singleton().mainWebView()->resizeTo(WKDoubleGetValue(widthWK), WKDoubleGetValue(heightWK));
789         return nullptr;
790     }
791
792     if (WKStringIsEqualToUTF8CString(messageName, "IsGeolocationClientActive")) {
793         bool isActive = TestController::singleton().isGeolocationProviderActive();
794         WKRetainPtr<WKTypeRef> result(AdoptWK, WKBooleanCreate(isActive));
795         return result;
796     }
797
798     if (WKStringIsEqualToUTF8CString(messageName, "IsWorkQueueEmpty")) {
799         bool isEmpty = TestController::singleton().workQueueManager().isWorkQueueEmpty();
800         WKRetainPtr<WKTypeRef> result(AdoptWK, WKBooleanCreate(isEmpty));
801         return result;
802     }
803
804     if (WKStringIsEqualToUTF8CString(messageName, "SecureEventInputIsEnabled")) {
805 #if PLATFORM(MAC) && !PLATFORM(IOS)
806         WKRetainPtr<WKBooleanRef> result(AdoptWK, WKBooleanCreate(IsSecureEventInputEnabled()));
807 #else
808         WKRetainPtr<WKBooleanRef> result(AdoptWK, WKBooleanCreate(false));
809 #endif
810         return result;
811     }
812
813     if (WKStringIsEqualToUTF8CString(messageName, "SetAlwaysAcceptCookies")) {
814         WKBooleanRef accept = static_cast<WKBooleanRef>(messageBody);
815         WKHTTPCookieAcceptPolicy policy = WKBooleanGetValue(accept) ? kWKHTTPCookieAcceptPolicyAlways : kWKHTTPCookieAcceptPolicyOnlyFromMainDocumentDomain;
816         // FIXME: This updates the policy in WebProcess and in NetworkProcess asynchronously, which might break some tests' expectations.
817         WKCookieManagerSetHTTPCookieAcceptPolicy(WKContextGetCookieManager(TestController::singleton().context()), policy);
818         return nullptr;
819     }
820
821     if (WKStringIsEqualToUTF8CString(messageName, "SetCookieStoragePartitioningEnabled")) {
822         WKBooleanRef accept = static_cast<WKBooleanRef>(messageBody);
823         WKCookieManagerSetCookieStoragePartitioningEnabled(WKContextGetCookieManager(TestController::singleton().context()), WKBooleanGetValue(accept));
824         return nullptr;
825     }
826
827     if (WKStringIsEqualToUTF8CString(messageName, "SetAllowsAnySSLCertificate")) {
828         TestController::singleton().setAllowsAnySSLCertificate(WKBooleanGetValue(static_cast<WKBooleanRef>(messageBody)));
829         return nullptr;
830     }
831
832     if (WKStringIsEqualToUTF8CString(messageName, "ImageCountInGeneralPasteboard")) {
833         unsigned count = TestController::singleton().imageCountInGeneralPasteboard();
834         WKRetainPtr<WKUInt64Ref> result(AdoptWK, WKUInt64Create(count));
835         return result;
836     }
837     
838     if (WKStringIsEqualToUTF8CString(messageName, "DeleteAllIndexedDatabases")) {
839         WKWebsiteDataStoreRemoveAllIndexedDatabases(WKContextGetWebsiteDataStore(TestController::singleton().context()));
840         return nullptr;
841     }
842
843 #if PLATFORM(MAC)
844     if (WKStringIsEqualToUTF8CString(messageName, "ConnectMockGamepad")) {
845         ASSERT(WKGetTypeID(messageBody) == WKUInt64GetTypeID());
846
847         uint64_t index = WKUInt64GetValue(static_cast<WKUInt64Ref>(messageBody));
848         WebCoreTestSupport::connectMockGamepad(index);
849         
850         return nullptr;
851     }
852
853     if (WKStringIsEqualToUTF8CString(messageName, "DisconnectMockGamepad")) {
854         ASSERT(WKGetTypeID(messageBody) == WKUInt64GetTypeID());
855
856         uint64_t index = WKUInt64GetValue(static_cast<WKUInt64Ref>(messageBody));
857         WebCoreTestSupport::disconnectMockGamepad(index);
858
859         return nullptr;
860     }
861
862     if (WKStringIsEqualToUTF8CString(messageName, "SetMockGamepadDetails")) {
863         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
864
865         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
866         WKRetainPtr<WKStringRef> gamepadIndexKey(AdoptWK, WKStringCreateWithUTF8CString("GamepadIndex"));
867         WKRetainPtr<WKStringRef> gamepadIDKey(AdoptWK, WKStringCreateWithUTF8CString("GamepadID"));
868         WKRetainPtr<WKStringRef> axisCountKey(AdoptWK, WKStringCreateWithUTF8CString("AxisCount"));
869         WKRetainPtr<WKStringRef> buttonCountKey(AdoptWK, WKStringCreateWithUTF8CString("ButtonCount"));
870
871         WKUInt64Ref gamepadIndex = static_cast<WKUInt64Ref>(WKDictionaryGetItemForKey(messageBodyDictionary, gamepadIndexKey.get()));
872         WKStringRef gamepadID = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, gamepadIDKey.get()));
873         WKUInt64Ref axisCount = static_cast<WKUInt64Ref>(WKDictionaryGetItemForKey(messageBodyDictionary, axisCountKey.get()));
874         WKUInt64Ref buttonCount = static_cast<WKUInt64Ref>(WKDictionaryGetItemForKey(messageBodyDictionary, buttonCountKey.get()));
875
876         WebCoreTestSupport::setMockGamepadDetails(WKUInt64GetValue(gamepadIndex), toWTFString(gamepadID), WKUInt64GetValue(axisCount), WKUInt64GetValue(buttonCount));
877         return nullptr;
878     }
879
880     if (WKStringIsEqualToUTF8CString(messageName, "SetMockGamepadAxisValue")) {
881         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
882
883         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
884         WKRetainPtr<WKStringRef> gamepadIndexKey(AdoptWK, WKStringCreateWithUTF8CString("GamepadIndex"));
885         WKRetainPtr<WKStringRef> axisIndexKey(AdoptWK, WKStringCreateWithUTF8CString("AxisIndex"));
886         WKRetainPtr<WKStringRef> valueKey(AdoptWK, WKStringCreateWithUTF8CString("Value"));
887
888         WKUInt64Ref gamepadIndex = static_cast<WKUInt64Ref>(WKDictionaryGetItemForKey(messageBodyDictionary, gamepadIndexKey.get()));
889         WKUInt64Ref axisIndex = static_cast<WKUInt64Ref>(WKDictionaryGetItemForKey(messageBodyDictionary, axisIndexKey.get()));
890         WKDoubleRef value = static_cast<WKDoubleRef>(WKDictionaryGetItemForKey(messageBodyDictionary, valueKey.get()));
891
892         WebCoreTestSupport::setMockGamepadAxisValue(WKUInt64GetValue(gamepadIndex), WKUInt64GetValue(axisIndex), WKDoubleGetValue(value));
893
894         return nullptr;
895     }
896
897     if (WKStringIsEqualToUTF8CString(messageName, "SetMockGamepadButtonValue")) {
898         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
899
900         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
901         WKRetainPtr<WKStringRef> gamepadIndexKey(AdoptWK, WKStringCreateWithUTF8CString("GamepadIndex"));
902         WKRetainPtr<WKStringRef> buttonIndexKey(AdoptWK, WKStringCreateWithUTF8CString("ButtonIndex"));
903         WKRetainPtr<WKStringRef> valueKey(AdoptWK, WKStringCreateWithUTF8CString("Value"));
904
905         WKUInt64Ref gamepadIndex = static_cast<WKUInt64Ref>(WKDictionaryGetItemForKey(messageBodyDictionary, gamepadIndexKey.get()));
906         WKUInt64Ref buttonIndex = static_cast<WKUInt64Ref>(WKDictionaryGetItemForKey(messageBodyDictionary, buttonIndexKey.get()));
907         WKDoubleRef value = static_cast<WKDoubleRef>(WKDictionaryGetItemForKey(messageBodyDictionary, valueKey.get()));
908
909         WebCoreTestSupport::setMockGamepadButtonValue(WKUInt64GetValue(gamepadIndex), WKUInt64GetValue(buttonIndex), WKDoubleGetValue(value));
910
911         return nullptr;
912     }
913 #endif // PLATFORM(MAC)
914
915     if (WKStringIsEqualToUTF8CString(messageName, "UserMediaPermissionRequestCountForOrigin")) {
916         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
917         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
918
919         WKRetainPtr<WKStringRef> originKey(AdoptWK, WKStringCreateWithUTF8CString("origin"));
920         WKStringRef originWK = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, originKey.get()));
921
922         WKRetainPtr<WKStringRef> parentOriginKey(AdoptWK, WKStringCreateWithUTF8CString("parentOrigin"));
923         WKStringRef parentOriginWK = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, parentOriginKey.get()));
924         
925         unsigned count = TestController::singleton().userMediaPermissionRequestCountForOrigin(originWK, parentOriginWK);
926         WKRetainPtr<WKUInt64Ref> result(AdoptWK, WKUInt64Create(count));
927         return result;
928     }
929
930     if (WKStringIsEqualToUTF8CString(messageName, "SetStatisticsLastSeen")) {
931         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
932         
933         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
934         WKRetainPtr<WKStringRef> hostNameKey(AdoptWK, WKStringCreateWithUTF8CString("HostName"));
935         WKRetainPtr<WKStringRef> valueKey(AdoptWK, WKStringCreateWithUTF8CString("Value"));
936         
937         WKStringRef hostName = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, hostNameKey.get()));
938         WKDoubleRef value = static_cast<WKDoubleRef>(WKDictionaryGetItemForKey(messageBodyDictionary, valueKey.get()));
939         
940         TestController::singleton().setStatisticsLastSeen(hostName, WKDoubleGetValue(value));
941         
942         return nullptr;
943     }
944     
945     if (WKStringIsEqualToUTF8CString(messageName, "SetStatisticsPrevalentResource")) {
946         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
947
948         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
949         WKRetainPtr<WKStringRef> hostNameKey(AdoptWK, WKStringCreateWithUTF8CString("HostName"));
950         WKRetainPtr<WKStringRef> valueKey(AdoptWK, WKStringCreateWithUTF8CString("Value"));
951
952         WKStringRef hostName = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, hostNameKey.get()));
953         WKBooleanRef value = static_cast<WKBooleanRef>(WKDictionaryGetItemForKey(messageBodyDictionary, valueKey.get()));
954
955         TestController::singleton().setStatisticsPrevalentResource(hostName, WKBooleanGetValue(value));
956         return nullptr;
957     }
958
959     if (WKStringIsEqualToUTF8CString(messageName, "IsStatisticsPrevalentResource")) {
960         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
961
962         WKStringRef hostName = static_cast<WKStringRef>(messageBody);
963         bool isPrevalent = TestController::singleton().isStatisticsPrevalentResource(hostName);
964         WKRetainPtr<WKTypeRef> result(AdoptWK, WKBooleanCreate(isPrevalent));
965         return result;
966     }
967
968     if (WKStringIsEqualToUTF8CString(messageName, "IsStatisticsRegisteredAsSubFrameUnder")) {
969         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
970         
971         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
972         WKRetainPtr<WKStringRef> subFrameHostKey(AdoptWK, WKStringCreateWithUTF8CString("SubFrameHost"));
973         WKRetainPtr<WKStringRef> topFrameHostKey(AdoptWK, WKStringCreateWithUTF8CString("TopFrameHost"));
974         
975         WKStringRef subFrameHost = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, subFrameHostKey.get()));
976         WKStringRef topFrameHost = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, topFrameHostKey.get()));
977
978         bool isRegisteredAsSubFrameUnder = TestController::singleton().isStatisticsRegisteredAsSubFrameUnder(subFrameHost, topFrameHost);
979         WKRetainPtr<WKTypeRef> result(AdoptWK, WKBooleanCreate(isRegisteredAsSubFrameUnder));
980         return result;
981     }
982     
983     if (WKStringIsEqualToUTF8CString(messageName, "IsStatisticsRegisteredAsRedirectingTo")) {
984         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
985         
986         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
987         WKRetainPtr<WKStringRef> hostRedirectedFromKey(AdoptWK, WKStringCreateWithUTF8CString("HostRedirectedFrom"));
988         WKRetainPtr<WKStringRef> hostRedirectedToKey(AdoptWK, WKStringCreateWithUTF8CString("HostRedirectedTo"));
989         
990         WKStringRef hostRedirectedFrom = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, hostRedirectedFromKey.get()));
991         WKStringRef hostRedirectedTo = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, hostRedirectedToKey.get()));
992         
993         bool isRegisteredAsRedirectingTo = TestController::singleton().isStatisticsRegisteredAsRedirectingTo(hostRedirectedFrom, hostRedirectedTo);
994         WKRetainPtr<WKTypeRef> result(AdoptWK, WKBooleanCreate(isRegisteredAsRedirectingTo));
995         return result;
996     }
997     
998     if (WKStringIsEqualToUTF8CString(messageName, "SetStatisticsHasHadUserInteraction")) {
999         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
1000         
1001         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
1002         WKRetainPtr<WKStringRef> hostNameKey(AdoptWK, WKStringCreateWithUTF8CString("HostName"));
1003         WKRetainPtr<WKStringRef> valueKey(AdoptWK, WKStringCreateWithUTF8CString("Value"));
1004         
1005         WKStringRef hostName = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, hostNameKey.get()));
1006         WKBooleanRef value = static_cast<WKBooleanRef>(WKDictionaryGetItemForKey(messageBodyDictionary, valueKey.get()));
1007         
1008         TestController::singleton().setStatisticsHasHadUserInteraction(hostName, WKBooleanGetValue(value));
1009         return nullptr;
1010     }
1011
1012     if (WKStringIsEqualToUTF8CString(messageName, "IsStatisticsHasHadUserInteraction")) {
1013         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
1014         
1015         WKStringRef hostName = static_cast<WKStringRef>(messageBody);
1016         bool hasHadUserInteraction = TestController::singleton().isStatisticsHasHadUserInteraction(hostName);
1017         WKRetainPtr<WKTypeRef> result(AdoptWK, WKBooleanCreate(hasHadUserInteraction));
1018         return result;
1019     }
1020     
1021     if (WKStringIsEqualToUTF8CString(messageName, "SetStatisticsGrandfathered")) {
1022         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
1023         
1024         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
1025         WKRetainPtr<WKStringRef> hostNameKey(AdoptWK, WKStringCreateWithUTF8CString("HostName"));
1026         WKRetainPtr<WKStringRef> valueKey(AdoptWK, WKStringCreateWithUTF8CString("Value"));
1027         
1028         WKStringRef hostName = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, hostNameKey.get()));
1029         WKBooleanRef value = static_cast<WKBooleanRef>(WKDictionaryGetItemForKey(messageBodyDictionary, valueKey.get()));
1030         
1031         TestController::singleton().setStatisticsGrandfathered(hostName, WKBooleanGetValue(value));
1032         return nullptr;
1033     }
1034     
1035     if (WKStringIsEqualToUTF8CString(messageName, "IsStatisticsGrandfathered")) {
1036         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
1037         
1038         WKStringRef hostName = static_cast<WKStringRef>(messageBody);
1039         bool isGrandfathered = TestController::singleton().isStatisticsGrandfathered(hostName);
1040         WKRetainPtr<WKTypeRef> result(AdoptWK, WKBooleanCreate(isGrandfathered));
1041         return result;
1042     }
1043     
1044     if (WKStringIsEqualToUTF8CString(messageName, "SetStatisticsSubframeUnderTopFrameOrigin")) {
1045         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
1046         
1047         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
1048         WKRetainPtr<WKStringRef> hostNameKey(AdoptWK, WKStringCreateWithUTF8CString("HostName"));
1049         WKRetainPtr<WKStringRef> topFrameHostNameKey(AdoptWK, WKStringCreateWithUTF8CString("TopFrameHostName"));
1050         
1051         WKStringRef hostName = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, hostNameKey.get()));
1052         WKStringRef topFrameHostName = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, topFrameHostNameKey.get()));
1053
1054         TestController::singleton().setStatisticsSubframeUnderTopFrameOrigin(hostName, topFrameHostName);
1055         return nullptr;
1056     }
1057     
1058     if (WKStringIsEqualToUTF8CString(messageName, "SetStatisticsSubresourceUnderTopFrameOrigin")) {
1059         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
1060         
1061         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
1062         WKRetainPtr<WKStringRef> hostNameKey(AdoptWK, WKStringCreateWithUTF8CString("HostName"));
1063         WKRetainPtr<WKStringRef> topFrameHostNameKey(AdoptWK, WKStringCreateWithUTF8CString("TopFrameHostName"));
1064         
1065         WKStringRef hostName = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, hostNameKey.get()));
1066         WKStringRef topFrameHostName = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, topFrameHostNameKey.get()));
1067         
1068         TestController::singleton().setStatisticsSubresourceUnderTopFrameOrigin(hostName, topFrameHostName);
1069         return nullptr;
1070     }
1071     
1072     if (WKStringIsEqualToUTF8CString(messageName, "SetStatisticsSubresourceUniqueRedirectTo")) {
1073         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
1074         
1075         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
1076         WKRetainPtr<WKStringRef> hostNameKey(AdoptWK, WKStringCreateWithUTF8CString("HostName"));
1077         WKRetainPtr<WKStringRef> hostNameRedirectedToKey(AdoptWK, WKStringCreateWithUTF8CString("HostNameRedirectedTo"));
1078         
1079         WKStringRef hostName = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, hostNameKey.get()));
1080         WKStringRef hostNameRedirectedTo = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, hostNameRedirectedToKey.get()));
1081         
1082         TestController::singleton().setStatisticsSubresourceUniqueRedirectTo(hostName, hostNameRedirectedTo);
1083         return nullptr;
1084     }
1085
1086     if (WKStringIsEqualToUTF8CString(messageName, "SetStatisticsTimeToLiveUserInteraction")) {
1087         ASSERT(WKGetTypeID(messageBody) == WKDoubleGetTypeID());
1088         WKDoubleRef seconds = static_cast<WKDoubleRef>(messageBody);
1089         TestController::singleton().setStatisticsTimeToLiveUserInteraction(WKDoubleGetValue(seconds));
1090         return nullptr;
1091     }
1092     
1093     if (WKStringIsEqualToUTF8CString(messageName, "SetStatisticsTimeToLiveCookiePartitionFree")) {
1094         ASSERT(WKGetTypeID(messageBody) == WKDoubleGetTypeID());
1095         WKDoubleRef seconds = static_cast<WKDoubleRef>(messageBody);
1096         TestController::singleton().setStatisticsTimeToLiveCookiePartitionFree(WKDoubleGetValue(seconds));
1097         return nullptr;
1098     }
1099
1100     if (WKStringIsEqualToUTF8CString(messageName, "StatisticsProcessStatisticsAndDataRecords")) {
1101         TestController::singleton().statisticsProcessStatisticsAndDataRecords();
1102         return nullptr;
1103     }
1104     
1105     if (WKStringIsEqualToUTF8CString(messageName, "StatisticsUpdateCookiePartitioning")) {
1106         TestController::singleton().statisticsUpdateCookiePartitioning();
1107         return nullptr;
1108     }
1109
1110     if (WKStringIsEqualToUTF8CString(messageName, "StatisticsSetShouldPartitionCookiesForHost")) {
1111         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
1112         
1113         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
1114         WKRetainPtr<WKStringRef> hostNameKey(AdoptWK, WKStringCreateWithUTF8CString("HostName"));
1115         WKRetainPtr<WKStringRef> valueKey(AdoptWK, WKStringCreateWithUTF8CString("Value"));
1116         
1117         WKStringRef hostName = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, hostNameKey.get()));
1118         WKBooleanRef value = static_cast<WKBooleanRef>(WKDictionaryGetItemForKey(messageBodyDictionary, valueKey.get()));
1119         
1120         TestController::singleton().statisticsSetShouldPartitionCookiesForHost(hostName, WKBooleanGetValue(value));
1121         return nullptr;
1122     }
1123     
1124     if (WKStringIsEqualToUTF8CString(messageName, "StatisticsSubmitTelemetry")) {
1125         TestController::singleton().statisticsSubmitTelemetry();
1126         return nullptr;
1127     }
1128     
1129     if (WKStringIsEqualToUTF8CString(messageName, "StatisticsNotifyPagesWhenDataRecordsWereScanned")) {
1130         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
1131         WKBooleanRef value = static_cast<WKBooleanRef>(messageBody);
1132         TestController::singleton().setStatisticsNotifyPagesWhenDataRecordsWereScanned(WKBooleanGetValue(value));
1133         return nullptr;
1134     }
1135
1136     if (WKStringIsEqualToUTF8CString(messageName, "StatisticsNotifyPagesWhenTelemetryWasCaptured")) {
1137         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
1138         WKBooleanRef value = static_cast<WKBooleanRef>(messageBody);
1139         TestController::singleton().setStatisticsNotifyPagesWhenTelemetryWasCaptured(WKBooleanGetValue(value));
1140         return nullptr;
1141     }
1142     
1143     if (WKStringIsEqualToUTF8CString(messageName, "StatisticsShouldClassifyResourcesBeforeDataRecordsRemoval")) {
1144         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
1145         WKBooleanRef value = static_cast<WKBooleanRef>(messageBody);
1146         TestController::singleton().setStatisticsShouldClassifyResourcesBeforeDataRecordsRemoval(WKBooleanGetValue(value));
1147         return nullptr;
1148     }
1149
1150     if (WKStringIsEqualToUTF8CString(messageName, "SetStatisticsMinimumTimeBetweenDataRecordsRemoval")) {
1151         ASSERT(WKGetTypeID(messageBody) == WKDoubleGetTypeID());
1152         WKDoubleRef seconds = static_cast<WKDoubleRef>(messageBody);
1153         TestController::singleton().setStatisticsMinimumTimeBetweenDataRecordsRemoval(WKDoubleGetValue(seconds));
1154         return nullptr;
1155     }
1156     
1157     if (WKStringIsEqualToUTF8CString(messageName, "SetStatisticsGrandfatheringTime")) {
1158         ASSERT(WKGetTypeID(messageBody) == WKDoubleGetTypeID());
1159         WKDoubleRef seconds = static_cast<WKDoubleRef>(messageBody);
1160         TestController::singleton().setStatisticsGrandfatheringTime(WKDoubleGetValue(seconds));
1161         return nullptr;
1162     }
1163     
1164     if (WKStringIsEqualToUTF8CString(messageName, "SetMaxStatisticsEntries")) {
1165         ASSERT(WKGetTypeID(messageBody) == WKUInt64GetTypeID());
1166         WKUInt64Ref entries = static_cast<WKUInt64Ref>(messageBody);
1167         TestController::singleton().setStatisticsMaxStatisticsEntries(WKUInt64GetValue(entries));
1168         return nullptr;
1169     }
1170     
1171     if (WKStringIsEqualToUTF8CString(messageName, "SetPruneEntriesDownTo")) {
1172         ASSERT(WKGetTypeID(messageBody) == WKUInt64GetTypeID());
1173         WKUInt64Ref entries = static_cast<WKUInt64Ref>(messageBody);
1174         TestController::singleton().setStatisticsPruneEntriesDownTo(WKUInt64GetValue(entries));
1175         return nullptr;
1176     }
1177     
1178     if (WKStringIsEqualToUTF8CString(messageName, "StatisticsClearInMemoryAndPersistentStore")) {
1179         TestController::singleton().statisticsClearInMemoryAndPersistentStore();
1180         return nullptr;
1181     }
1182     
1183     if (WKStringIsEqualToUTF8CString(messageName, "StatisticsClearInMemoryAndPersistentStoreModifiedSinceHours")) {
1184         ASSERT(WKGetTypeID(messageBody) == WKUInt64GetTypeID());
1185         WKUInt64Ref hours = static_cast<WKUInt64Ref>(messageBody);
1186         TestController::singleton().statisticsClearInMemoryAndPersistentStoreModifiedSinceHours(WKUInt64GetValue(hours));
1187         return nullptr;
1188     }
1189     
1190     if (WKStringIsEqualToUTF8CString(messageName, "StatisticsClearThroughWebsiteDataRemoval")) {
1191         TestController::singleton().statisticsClearThroughWebsiteDataRemoval();
1192         return nullptr;
1193     }
1194     
1195     if (WKStringIsEqualToUTF8CString(messageName, "StatisticsResetToConsistentState")) {
1196         TestController::singleton().statisticsResetToConsistentState();
1197         return nullptr;
1198     }
1199
1200     if (WKStringIsEqualToUTF8CString(messageName, "RemoveAllSessionCredentials")) {
1201         TestController::singleton().removeAllSessionCredentials();
1202         return nullptr;
1203     }
1204
1205     if (WKStringIsEqualToUTF8CString(messageName, "ClearDOMCache")) {
1206         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
1207         WKStringRef origin = static_cast<WKStringRef>(messageBody);
1208
1209         TestController::singleton().clearDOMCache(origin);
1210         return nullptr;
1211     }
1212
1213     if (WKStringIsEqualToUTF8CString(messageName, "ClearDOMCaches")) {
1214         TestController::singleton().clearDOMCaches();
1215         return nullptr;
1216     }
1217
1218     if (WKStringIsEqualToUTF8CString(messageName, "HasDOMCache")) {
1219         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
1220         WKStringRef origin = static_cast<WKStringRef>(messageBody);
1221
1222         bool hasDOMCache = TestController::singleton().hasDOMCache(origin);
1223         WKRetainPtr<WKTypeRef> result(AdoptWK, WKBooleanCreate(hasDOMCache));
1224         return result;
1225     }
1226
1227     if (WKStringIsEqualToUTF8CString(messageName, "DOMCacheSize")) {
1228         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
1229         WKStringRef origin = static_cast<WKStringRef>(messageBody);
1230
1231         auto domCacheSize = TestController::singleton().domCacheSize(origin);
1232         WKRetainPtr<WKTypeRef> result(AdoptWK, WKUInt64Create(domCacheSize));
1233         return result;
1234     }
1235
1236     ASSERT_NOT_REACHED();
1237     return nullptr;
1238 }
1239
1240 void TestInvocation::runUISideScriptAfterUpdateCallback(WKErrorRef, void* context)
1241 {
1242     UIScriptInvocationData* data = static_cast<UIScriptInvocationData*>(context);
1243     if (TestInvocation* invocation = data->testInvocation) {
1244         RELEASE_ASSERT(TestController::singleton().isCurrentInvocation(invocation));
1245         invocation->runUISideScript(data->scriptString.get(), data->callbackID);
1246     }
1247     delete data;
1248 }
1249
1250 void TestInvocation::runUISideScript(WKStringRef script, unsigned scriptCallbackID)
1251 {
1252     m_pendingUIScriptInvocationData = nullptr;
1253
1254     if (!m_UIScriptContext)
1255         m_UIScriptContext = std::make_unique<UIScriptContext>(*this);
1256     
1257     m_UIScriptContext->runUIScript(toWTFString(script), scriptCallbackID);
1258 }
1259
1260 void TestInvocation::uiScriptDidComplete(const String& result, unsigned scriptCallbackID)
1261 {
1262     WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("CallUISideScriptCallback"));
1263
1264     WKRetainPtr<WKMutableDictionaryRef> messageBody(AdoptWK, WKMutableDictionaryCreate());
1265     WKRetainPtr<WKStringRef> resultKey(AdoptWK, WKStringCreateWithUTF8CString("Result"));
1266     WKRetainPtr<WKStringRef> callbackIDKey(AdoptWK, WKStringCreateWithUTF8CString("CallbackID"));
1267     WKRetainPtr<WKUInt64Ref> callbackIDValue = adoptWK(WKUInt64Create(scriptCallbackID));
1268
1269     WKDictionarySetItem(messageBody.get(), resultKey.get(), toWK(result).get());
1270     WKDictionarySetItem(messageBody.get(), callbackIDKey.get(), callbackIDValue.get());
1271
1272     WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), messageBody.get());
1273 }
1274
1275 void TestInvocation::outputText(const WTF::String& text)
1276 {
1277     m_textOutput.append(text);
1278 }
1279
1280 void TestInvocation::didBeginSwipe()
1281 {
1282     WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("CallDidBeginSwipeCallback"));
1283     WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
1284 }
1285
1286 void TestInvocation::willEndSwipe()
1287 {
1288     WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("CallWillEndSwipeCallback"));
1289     WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
1290 }
1291
1292 void TestInvocation::didEndSwipe()
1293 {
1294     WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("CallDidEndSwipeCallback"));
1295     WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
1296 }
1297
1298 void TestInvocation::didRemoveSwipeSnapshot()
1299 {
1300     WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("CallDidRemoveSwipeSnapshotCallback"));
1301     WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
1302 }
1303
1304 void TestInvocation::notifyDownloadDone()
1305 {
1306     WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("NotifyDownloadDone"));
1307     WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
1308 }
1309
1310 void TestInvocation::didClearStatisticsThroughWebsiteDataRemoval()
1311 {
1312     WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("CallDidClearStatisticsThroughWebsiteDataRemoval"));
1313     WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
1314 }
1315
1316 void TestInvocation::didRemoveAllSessionCredentials()
1317 {
1318     WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("CallDidRemoveAllSessionCredentialsCallback"));
1319     WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
1320 }
1321
1322 } // namespace WTR