Add support for Device Orientation / Motion permission API
[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 <wtf/StdLibExtras.h>
46 #include <wtf/text/CString.h>
47
48 #if PLATFORM(MAC) && !PLATFORM(IOS_FAMILY)
49 #include <Carbon/Carbon.h>
50 #endif
51
52 #if PLATFORM(COCOA)
53 #include <WebKit/WKPagePrivateMac.h>
54 #endif
55
56 #if PLATFORM(WIN)
57 #include <io.h>
58 #define isatty _isatty
59 #else
60 #include <unistd.h>
61 #endif
62
63 using namespace JSC;
64 using namespace WebKit;
65 using namespace std;
66
67 namespace WTR {
68
69 TestInvocation::TestInvocation(WKURLRef url, const TestOptions& options)
70     : m_options(options)
71     , m_url(url)
72 {
73     WKRetainPtr<WKStringRef> urlString = adoptWK(WKURLCopyString(m_url.get()));
74
75     size_t stringLength = WKStringGetLength(urlString.get());
76
77     Vector<char> urlVector;
78     urlVector.resize(stringLength + 1);
79
80     WKStringGetUTF8CString(urlString.get(), urlVector.data(), stringLength + 1);
81
82     m_urlString = String(urlVector.data(), stringLength);
83
84     // FIXME: Avoid mutating the setting via a test directory like this.
85     m_dumpFrameLoadCallbacks = urlContains("loading/");
86 }
87
88 TestInvocation::~TestInvocation()
89 {
90     if (m_pendingUIScriptInvocationData)
91         m_pendingUIScriptInvocationData->testInvocation = nullptr;
92 }
93
94 WKURLRef TestInvocation::url() const
95 {
96     return m_url.get();
97 }
98
99 bool TestInvocation::urlContains(const char* searchString) const
100 {
101     return m_urlString.containsIgnoringASCIICase(searchString);
102 }
103
104 void TestInvocation::setIsPixelTest(const std::string& expectedPixelHash)
105 {
106     m_dumpPixels = true;
107     m_expectedPixelHash = expectedPixelHash;
108 }
109
110 WTF::Seconds TestInvocation::shortTimeout() const
111 {
112     if (!m_timeout) {
113         // Running WKTR directly, without webkitpy.
114         return TestController::defaultShortTimeout;
115     }
116
117     // This is not exactly correct for the way short timeout is used - it should not depend on whether a test is "slow",
118     // but it currently does. There is no way to know what a normal test's timeout is, as webkitpy only passes timeouts
119     // for each test individually.
120     // But there shouldn't be any observable negative consequences from this.
121     return m_timeout / 4;
122 }
123
124 bool TestInvocation::shouldLogHistoryClientCallbacks() const
125 {
126     return urlContains("globalhistory/");
127 }
128
129 WKRetainPtr<WKMutableDictionaryRef> TestInvocation::createTestSettingsDictionary()
130 {
131     WKRetainPtr<WKMutableDictionaryRef> beginTestMessageBody = adoptWK(WKMutableDictionaryCreate());
132
133     WKRetainPtr<WKStringRef> useFlexibleViewportKey = adoptWK(WKStringCreateWithUTF8CString("UseFlexibleViewport"));
134     WKRetainPtr<WKBooleanRef> useFlexibleViewportValue = adoptWK(WKBooleanCreate(options().useFlexibleViewport));
135     WKDictionarySetItem(beginTestMessageBody.get(), useFlexibleViewportKey.get(), useFlexibleViewportValue.get());
136
137     WKRetainPtr<WKStringRef> dumpPixelsKey = adoptWK(WKStringCreateWithUTF8CString("DumpPixels"));
138     WKRetainPtr<WKBooleanRef> dumpPixelsValue = adoptWK(WKBooleanCreate(m_dumpPixels));
139     WKDictionarySetItem(beginTestMessageBody.get(), dumpPixelsKey.get(), dumpPixelsValue.get());
140
141     WKRetainPtr<WKStringRef> useWaitToDumpWatchdogTimerKey = adoptWK(WKStringCreateWithUTF8CString("UseWaitToDumpWatchdogTimer"));
142     WKRetainPtr<WKBooleanRef> useWaitToDumpWatchdogTimerValue = adoptWK(WKBooleanCreate(TestController::singleton().useWaitToDumpWatchdogTimer()));
143     WKDictionarySetItem(beginTestMessageBody.get(), useWaitToDumpWatchdogTimerKey.get(), useWaitToDumpWatchdogTimerValue.get());
144
145     WKRetainPtr<WKStringRef> timeoutKey = adoptWK(WKStringCreateWithUTF8CString("Timeout"));
146     WKRetainPtr<WKUInt64Ref> timeoutValue = adoptWK(WKUInt64Create(m_timeout.milliseconds()));
147     WKDictionarySetItem(beginTestMessageBody.get(), timeoutKey.get(), timeoutValue.get());
148
149     WKRetainPtr<WKStringRef> dumpJSConsoleLogInStdErrKey = adoptWK(WKStringCreateWithUTF8CString("DumpJSConsoleLogInStdErr"));
150     WKRetainPtr<WKBooleanRef> dumpJSConsoleLogInStdErrValue = adoptWK(WKBooleanCreate(m_dumpJSConsoleLogInStdErr));
151     WKDictionarySetItem(beginTestMessageBody.get(), dumpJSConsoleLogInStdErrKey.get(), dumpJSConsoleLogInStdErrValue.get());
152     
153     return beginTestMessageBody;
154 }
155
156 void TestInvocation::invoke()
157 {
158     TestController::singleton().configureViewForTest(*this);
159
160     WKPageSetAddsVisitedLinks(TestController::singleton().mainWebView()->page(), false);
161
162     m_textOutput.clear();
163
164     TestController::singleton().setShouldLogHistoryClientCallbacks(shouldLogHistoryClientCallbacks());
165
166     WKCookieManagerSetHTTPCookieAcceptPolicy(WKContextGetCookieManager(TestController::singleton().context()), kWKHTTPCookieAcceptPolicyOnlyFromMainDocumentDomain);
167
168     // FIXME: We should clear out visited links here.
169
170     WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("BeginTest"));
171     auto beginTestMessageBody = createTestSettingsDictionary();
172     WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), beginTestMessageBody.get());
173
174     m_startedTesting = true;
175
176     bool shouldOpenExternalURLs = false;
177
178     TestController::singleton().runUntil(m_gotInitialResponse, TestController::noTimeout);
179     if (m_error)
180         goto end;
181
182     WKPageLoadURLWithShouldOpenExternalURLsPolicy(TestController::singleton().mainWebView()->page(), m_url.get(), shouldOpenExternalURLs);
183
184     TestController::singleton().runUntil(m_gotFinalMessage, TestController::noTimeout);
185     if (m_error)
186         goto end;
187
188     dumpResults();
189
190 end:
191 #if !PLATFORM(IOS_FAMILY)
192     if (m_gotInitialResponse)
193         WKInspectorClose(WKPageGetInspector(TestController::singleton().mainWebView()->page()));
194 #endif // !PLATFORM(IOS_FAMILY)
195
196     if (TestController::singleton().resetStateToConsistentValues(m_options, TestController::ResetStage::AfterTest))
197         return;
198
199     // The process is unresponsive, so let's start a new one.
200     TestController::singleton().terminateWebContentProcess();
201     // Make sure that we have a process, as invoke() will need one to send bundle messages for the next test.
202     TestController::singleton().reattachPageToWebProcess();
203 }
204
205 void TestInvocation::dumpWebProcessUnresponsiveness(const char* errorMessage)
206 {
207     fprintf(stderr, "%s", errorMessage);
208     char buffer[1024] = { };
209 #if PLATFORM(COCOA)
210     pid_t pid = WKPageGetProcessIdentifier(TestController::singleton().mainWebView()->page());
211     snprintf(buffer, sizeof(buffer), "#PROCESS UNRESPONSIVE - %s (pid %ld)\n", TestController::webProcessName(), static_cast<long>(pid));
212 #else
213     snprintf(buffer, sizeof(buffer), "#PROCESS UNRESPONSIVE - %s\n", TestController::webProcessName());
214 #endif
215
216     dump(errorMessage, buffer, true);
217     
218     if (!TestController::singleton().usingServerMode())
219         return;
220     
221     if (isatty(fileno(stdin)) || isatty(fileno(stderr)))
222         fputs("Grab an image of the stack, then hit enter...\n", stderr);
223     
224     if (!fgets(buffer, sizeof(buffer), stdin) || strcmp(buffer, "#SAMPLE FINISHED\n"))
225         fprintf(stderr, "Failed receive expected sample response, got:\n\t\"%s\"\nContinuing...\n", buffer);
226 }
227
228 void TestInvocation::dump(const char* textToStdout, const char* textToStderr, bool seenError)
229 {
230     printf("Content-Type: text/plain\n");
231     if (textToStdout)
232         fputs(textToStdout, stdout);
233     if (textToStderr)
234         fputs(textToStderr, stderr);
235
236     fputs("#EOF\n", stdout);
237     fputs("#EOF\n", stderr);
238     if (seenError)
239         fputs("#EOF\n", stdout);
240     fflush(stdout);
241     fflush(stderr);
242 }
243
244 void TestInvocation::forceRepaintDoneCallback(WKErrorRef error, void* context)
245 {
246     // The context may not be valid any more, e.g. if WebKit is invalidating callbacks at process exit.
247     if (error)
248         return;
249
250     TestInvocation* testInvocation = static_cast<TestInvocation*>(context);
251     RELEASE_ASSERT(TestController::singleton().isCurrentInvocation(testInvocation));
252
253     testInvocation->m_gotRepaint = true;
254     TestController::singleton().notifyDone();
255 }
256
257 void TestInvocation::dumpResults()
258 {
259     if (m_shouldDumpResourceLoadStatistics)
260         m_textOutput.append(m_savedResourceLoadStatistics.isNull() ? TestController::singleton().dumpResourceLoadStatistics() : m_savedResourceLoadStatistics);
261
262     if (m_shouldDumpAdClickAttribution)
263         m_textOutput.append(TestController::singleton().dumpAdClickAttribution());
264     
265     if (m_textOutput.length() || !m_audioResult)
266         dump(m_textOutput.toString().utf8().data());
267     else
268         dumpAudio(m_audioResult.get());
269
270     if (m_dumpPixels) {
271         if (m_pixelResult)
272             dumpPixelsAndCompareWithExpected(SnapshotResultType::WebContents, m_repaintRects.get(), m_pixelResult.get());
273         else if (m_pixelResultIsPending) {
274             m_gotRepaint = false;
275             WKPageForceRepaint(TestController::singleton().mainWebView()->page(), this, TestInvocation::forceRepaintDoneCallback);
276             TestController::singleton().runUntil(m_gotRepaint, TestController::noTimeout);
277             dumpPixelsAndCompareWithExpected(SnapshotResultType::WebView, m_repaintRects.get());
278         }
279     }
280
281     fputs("#EOF\n", stdout);
282     fflush(stdout);
283     fflush(stderr);
284 }
285
286 void TestInvocation::dumpAudio(WKDataRef audioData)
287 {
288     size_t length = WKDataGetSize(audioData);
289     if (!length)
290         return;
291
292     const unsigned char* data = WKDataGetBytes(audioData);
293
294     printf("Content-Type: audio/wav\n");
295     printf("Content-Length: %lu\n", static_cast<unsigned long>(length));
296
297     fwrite(data, 1, length, stdout);
298     printf("#EOF\n");
299     fprintf(stderr, "#EOF\n");
300 }
301
302 bool TestInvocation::compareActualHashToExpectedAndDumpResults(const char actualHash[33])
303 {
304     // Compute the hash of the bitmap context pixels
305     fprintf(stdout, "\nActualHash: %s\n", actualHash);
306
307     if (!m_expectedPixelHash.length())
308         return false;
309
310     ASSERT(m_expectedPixelHash.length() == 32);
311     fprintf(stdout, "\nExpectedHash: %s\n", m_expectedPixelHash.c_str());
312
313     // FIXME: Do case insensitive compare.
314     return m_expectedPixelHash == actualHash;
315 }
316
317 void TestInvocation::didReceiveMessageFromInjectedBundle(WKStringRef messageName, WKTypeRef messageBody)
318 {
319     if (WKStringIsEqualToUTF8CString(messageName, "Error")) {
320         // Set all states to true to stop spinning the runloop.
321         m_gotInitialResponse = true;
322         m_gotFinalMessage = true;
323         m_error = true;
324         TestController::singleton().notifyDone();
325         return;
326     }
327
328     if (WKStringIsEqualToUTF8CString(messageName, "Ack")) {
329         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
330         WKStringRef messageBodyString = static_cast<WKStringRef>(messageBody);
331         if (WKStringIsEqualToUTF8CString(messageBodyString, "BeginTest")) {
332             m_gotInitialResponse = true;
333             TestController::singleton().notifyDone();
334             return;
335         }
336
337         ASSERT_NOT_REACHED();
338     }
339
340     if (WKStringIsEqualToUTF8CString(messageName, "Done")) {
341         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
342         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
343
344         WKRetainPtr<WKStringRef> pixelResultIsPendingKey = adoptWK(WKStringCreateWithUTF8CString("PixelResultIsPending"));
345         WKBooleanRef pixelResultIsPending = static_cast<WKBooleanRef>(WKDictionaryGetItemForKey(messageBodyDictionary, pixelResultIsPendingKey.get()));
346         m_pixelResultIsPending = WKBooleanGetValue(pixelResultIsPending);
347
348         if (!m_pixelResultIsPending) {
349             WKRetainPtr<WKStringRef> pixelResultKey = adoptWK(WKStringCreateWithUTF8CString("PixelResult"));
350             m_pixelResult = static_cast<WKImageRef>(WKDictionaryGetItemForKey(messageBodyDictionary, pixelResultKey.get()));
351             ASSERT(!m_pixelResult || m_dumpPixels);
352         }
353
354         WKRetainPtr<WKStringRef> repaintRectsKey = adoptWK(WKStringCreateWithUTF8CString("RepaintRects"));
355         m_repaintRects = static_cast<WKArrayRef>(WKDictionaryGetItemForKey(messageBodyDictionary, repaintRectsKey.get()));
356
357         WKRetainPtr<WKStringRef> audioResultKey =  adoptWK(WKStringCreateWithUTF8CString("AudioResult"));
358         m_audioResult = static_cast<WKDataRef>(WKDictionaryGetItemForKey(messageBodyDictionary, audioResultKey.get()));
359
360         m_gotFinalMessage = true;
361         TestController::singleton().notifyDone();
362         return;
363     }
364
365     if (WKStringIsEqualToUTF8CString(messageName, "TextOutput")) {
366         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
367         WKStringRef textOutput = static_cast<WKStringRef>(messageBody);
368         m_textOutput.append(toWTFString(textOutput));
369         return;
370     }
371
372     if (WKStringIsEqualToUTF8CString(messageName, "DumpToStdErr")) {
373         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
374         WKStringRef textOutput = static_cast<WKStringRef>(messageBody);
375         fprintf(stderr, "%s", toWTFString(textOutput).utf8().data());
376         return;
377     }
378
379     if (WKStringIsEqualToUTF8CString(messageName, "BeforeUnloadReturnValue")) {
380         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
381         WKBooleanRef beforeUnloadReturnValue = static_cast<WKBooleanRef>(messageBody);
382         TestController::singleton().setBeforeUnloadReturnValue(WKBooleanGetValue(beforeUnloadReturnValue));
383         return;
384     }
385     
386     if (WKStringIsEqualToUTF8CString(messageName, "AddChromeInputField")) {
387         TestController::singleton().mainWebView()->addChromeInputField();
388         WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("CallAddChromeInputFieldCallback"));
389         WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
390         return;
391     }
392
393     if (WKStringIsEqualToUTF8CString(messageName, "RemoveChromeInputField")) {
394         TestController::singleton().mainWebView()->removeChromeInputField();
395         WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("CallRemoveChromeInputFieldCallback"));
396         WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
397         return;
398     }
399     
400     if (WKStringIsEqualToUTF8CString(messageName, "FocusWebView")) {
401         TestController::singleton().mainWebView()->makeWebViewFirstResponder();
402         WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("CallFocusWebViewCallback"));
403         WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
404         return;
405     }
406
407     if (WKStringIsEqualToUTF8CString(messageName, "SetBackingScaleFactor")) {
408         ASSERT(WKGetTypeID(messageBody) == WKDoubleGetTypeID());
409         double backingScaleFactor = WKDoubleGetValue(static_cast<WKDoubleRef>(messageBody));
410         WKPageSetCustomBackingScaleFactor(TestController::singleton().mainWebView()->page(), backingScaleFactor);
411
412         WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("CallSetBackingScaleFactorCallback"));
413         WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
414         return;
415     }
416
417     if (WKStringIsEqualToUTF8CString(messageName, "SimulateWebNotificationClick")) {
418         ASSERT(WKGetTypeID(messageBody) == WKUInt64GetTypeID());
419         uint64_t notificationID = WKUInt64GetValue(static_cast<WKUInt64Ref>(messageBody));
420         TestController::singleton().simulateWebNotificationClick(notificationID);
421         return;
422     }
423
424     if (WKStringIsEqualToUTF8CString(messageName, "SetAddsVisitedLinks")) {
425         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
426         WKBooleanRef enabledWK = static_cast<WKBooleanRef>(messageBody);
427         WKPageSetAddsVisitedLinks(TestController::singleton().mainWebView()->page(), WKBooleanGetValue(enabledWK));
428         return;
429     }
430
431     if (WKStringIsEqualToUTF8CString(messageName, "SetGeolocationPermission")) {
432         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
433         WKBooleanRef enabledWK = static_cast<WKBooleanRef>(messageBody);
434         TestController::singleton().setGeolocationPermission(WKBooleanGetValue(enabledWK));
435         return;
436     }
437
438     if (WKStringIsEqualToUTF8CString(messageName, "SetMockGeolocationPosition")) {
439         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
440         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
441
442         WKRetainPtr<WKStringRef> latitudeKeyWK(AdoptWK, WKStringCreateWithUTF8CString("latitude"));
443         WKDoubleRef latitudeWK = static_cast<WKDoubleRef>(WKDictionaryGetItemForKey(messageBodyDictionary, latitudeKeyWK.get()));
444         double latitude = WKDoubleGetValue(latitudeWK);
445
446         WKRetainPtr<WKStringRef> longitudeKeyWK(AdoptWK, WKStringCreateWithUTF8CString("longitude"));
447         WKDoubleRef longitudeWK = static_cast<WKDoubleRef>(WKDictionaryGetItemForKey(messageBodyDictionary, longitudeKeyWK.get()));
448         double longitude = WKDoubleGetValue(longitudeWK);
449
450         WKRetainPtr<WKStringRef> accuracyKeyWK(AdoptWK, WKStringCreateWithUTF8CString("accuracy"));
451         WKDoubleRef accuracyWK = static_cast<WKDoubleRef>(WKDictionaryGetItemForKey(messageBodyDictionary, accuracyKeyWK.get()));
452         double accuracy = WKDoubleGetValue(accuracyWK);
453
454         WKRetainPtr<WKStringRef> providesAltitudeKeyWK(AdoptWK, WKStringCreateWithUTF8CString("providesAltitude"));
455         WKBooleanRef providesAltitudeWK = static_cast<WKBooleanRef>(WKDictionaryGetItemForKey(messageBodyDictionary, providesAltitudeKeyWK.get()));
456         bool providesAltitude = WKBooleanGetValue(providesAltitudeWK);
457
458         WKRetainPtr<WKStringRef> altitudeKeyWK(AdoptWK, WKStringCreateWithUTF8CString("altitude"));
459         WKDoubleRef altitudeWK = static_cast<WKDoubleRef>(WKDictionaryGetItemForKey(messageBodyDictionary, altitudeKeyWK.get()));
460         double altitude = WKDoubleGetValue(altitudeWK);
461
462         WKRetainPtr<WKStringRef> providesAltitudeAccuracyKeyWK(AdoptWK, WKStringCreateWithUTF8CString("providesAltitudeAccuracy"));
463         WKBooleanRef providesAltitudeAccuracyWK = static_cast<WKBooleanRef>(WKDictionaryGetItemForKey(messageBodyDictionary, providesAltitudeAccuracyKeyWK.get()));
464         bool providesAltitudeAccuracy = WKBooleanGetValue(providesAltitudeAccuracyWK);
465
466         WKRetainPtr<WKStringRef> altitudeAccuracyKeyWK(AdoptWK, WKStringCreateWithUTF8CString("altitudeAccuracy"));
467         WKDoubleRef altitudeAccuracyWK = static_cast<WKDoubleRef>(WKDictionaryGetItemForKey(messageBodyDictionary, altitudeAccuracyKeyWK.get()));
468         double altitudeAccuracy = WKDoubleGetValue(altitudeAccuracyWK);
469
470         WKRetainPtr<WKStringRef> providesHeadingKeyWK(AdoptWK, WKStringCreateWithUTF8CString("providesHeading"));
471         WKBooleanRef providesHeadingWK = static_cast<WKBooleanRef>(WKDictionaryGetItemForKey(messageBodyDictionary, providesHeadingKeyWK.get()));
472         bool providesHeading = WKBooleanGetValue(providesHeadingWK);
473
474         WKRetainPtr<WKStringRef> headingKeyWK(AdoptWK, WKStringCreateWithUTF8CString("heading"));
475         WKDoubleRef headingWK = static_cast<WKDoubleRef>(WKDictionaryGetItemForKey(messageBodyDictionary, headingKeyWK.get()));
476         double heading = WKDoubleGetValue(headingWK);
477
478         WKRetainPtr<WKStringRef> providesSpeedKeyWK(AdoptWK, WKStringCreateWithUTF8CString("providesSpeed"));
479         WKBooleanRef providesSpeedWK = static_cast<WKBooleanRef>(WKDictionaryGetItemForKey(messageBodyDictionary, providesSpeedKeyWK.get()));
480         bool providesSpeed = WKBooleanGetValue(providesSpeedWK);
481
482         WKRetainPtr<WKStringRef> speedKeyWK(AdoptWK, WKStringCreateWithUTF8CString("speed"));
483         WKDoubleRef speedWK = static_cast<WKDoubleRef>(WKDictionaryGetItemForKey(messageBodyDictionary, speedKeyWK.get()));
484         double speed = WKDoubleGetValue(speedWK);
485
486         WKRetainPtr<WKStringRef> providesFloorLevelKeyWK(AdoptWK, WKStringCreateWithUTF8CString("providesFloorLevel"));
487         WKBooleanRef providesFloorLevelWK = static_cast<WKBooleanRef>(WKDictionaryGetItemForKey(messageBodyDictionary, providesFloorLevelKeyWK.get()));
488         bool providesFloorLevel = WKBooleanGetValue(providesFloorLevelWK);
489
490         WKRetainPtr<WKStringRef> floorLevelKeyWK(AdoptWK, WKStringCreateWithUTF8CString("floorLevel"));
491         WKDoubleRef floorLevelWK = static_cast<WKDoubleRef>(WKDictionaryGetItemForKey(messageBodyDictionary, floorLevelKeyWK.get()));
492         double floorLevel = WKDoubleGetValue(floorLevelWK);
493
494         TestController::singleton().setMockGeolocationPosition(latitude, longitude, accuracy, providesAltitude, altitude, providesAltitudeAccuracy, altitudeAccuracy, providesHeading, heading, providesSpeed, speed, providesFloorLevel, floorLevel);
495         return;
496     }
497
498     if (WKStringIsEqualToUTF8CString(messageName, "SetMockGeolocationPositionUnavailableError")) {
499         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
500         WKStringRef errorMessage = static_cast<WKStringRef>(messageBody);
501         TestController::singleton().setMockGeolocationPositionUnavailableError(errorMessage);
502         return;
503     }
504
505     if (WKStringIsEqualToUTF8CString(messageName, "SetUserMediaPermission")) {
506         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
507         WKBooleanRef enabledWK = static_cast<WKBooleanRef>(messageBody);
508         TestController::singleton().setUserMediaPermission(WKBooleanGetValue(enabledWK));
509         return;
510     }
511
512     if (WKStringIsEqualToUTF8CString(messageName, "ResetUserMediaPermission")) {
513         TestController::singleton().resetUserMediaPermission();
514         return;
515     }
516
517     if (WKStringIsEqualToUTF8CString(messageName, "SetUserMediaPersistentPermissionForOrigin")) {
518         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
519         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
520
521         WKRetainPtr<WKStringRef> permissionKeyWK(AdoptWK, WKStringCreateWithUTF8CString("permission"));
522         WKBooleanRef permissionWK = static_cast<WKBooleanRef>(WKDictionaryGetItemForKey(messageBodyDictionary, permissionKeyWK.get()));
523         bool permission = WKBooleanGetValue(permissionWK);
524
525         WKRetainPtr<WKStringRef> originKey(AdoptWK, WKStringCreateWithUTF8CString("origin"));
526         WKStringRef originWK = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, originKey.get()));
527
528         WKRetainPtr<WKStringRef> parentOriginKey(AdoptWK, WKStringCreateWithUTF8CString("parentOrigin"));
529         WKStringRef parentOriginWK = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, parentOriginKey.get()));
530
531         TestController::singleton().setUserMediaPersistentPermissionForOrigin(permission, originWK, parentOriginWK);
532         return;
533     }
534
535     if (WKStringIsEqualToUTF8CString(messageName, "ResetUserMediaPermissionRequestCountForOrigin")) {
536         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
537         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
538
539         WKRetainPtr<WKStringRef> originKey(AdoptWK, WKStringCreateWithUTF8CString("origin"));
540         WKStringRef originWK = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, originKey.get()));
541
542         WKRetainPtr<WKStringRef> parentOriginKey(AdoptWK, WKStringCreateWithUTF8CString("parentOrigin"));
543         WKStringRef parentOriginWK = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, parentOriginKey.get()));
544         
545         TestController::singleton().resetUserMediaPermissionRequestCountForOrigin(originWK, parentOriginWK);
546         return;
547     }
548
549     if (WKStringIsEqualToUTF8CString(messageName, "SetCacheModel")) {
550         ASSERT(WKGetTypeID(messageBody) == WKUInt64GetTypeID());
551         uint64_t model = WKUInt64GetValue(static_cast<WKUInt64Ref>(messageBody));
552         WKContextSetCacheModel(TestController::singleton().context(), model);
553         return;
554     }
555
556     if (WKStringIsEqualToUTF8CString(messageName, "SetCustomPolicyDelegate")) {
557         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
558         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
559
560         WKRetainPtr<WKStringRef> enabledKeyWK(AdoptWK, WKStringCreateWithUTF8CString("enabled"));
561         WKBooleanRef enabledWK = static_cast<WKBooleanRef>(WKDictionaryGetItemForKey(messageBodyDictionary, enabledKeyWK.get()));
562         bool enabled = WKBooleanGetValue(enabledWK);
563
564         WKRetainPtr<WKStringRef> permissiveKeyWK(AdoptWK, WKStringCreateWithUTF8CString("permissive"));
565         WKBooleanRef permissiveWK = static_cast<WKBooleanRef>(WKDictionaryGetItemForKey(messageBodyDictionary, permissiveKeyWK.get()));
566         bool permissive = WKBooleanGetValue(permissiveWK);
567
568         TestController::singleton().setCustomPolicyDelegate(enabled, permissive);
569         return;
570     }
571
572     if (WKStringIsEqualToUTF8CString(messageName, "SetHidden")) {
573         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
574         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
575
576         WKRetainPtr<WKStringRef> isInitialKeyWK(AdoptWK, WKStringCreateWithUTF8CString("hidden"));
577         WKBooleanRef hiddenWK = static_cast<WKBooleanRef>(WKDictionaryGetItemForKey(messageBodyDictionary, isInitialKeyWK.get()));
578         bool hidden = WKBooleanGetValue(hiddenWK);
579
580         TestController::singleton().setHidden(hidden);
581         return;
582     }
583
584     if (WKStringIsEqualToUTF8CString(messageName, "ProcessWorkQueue")) {
585         if (TestController::singleton().workQueueManager().processWorkQueue()) {
586             WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("WorkQueueProcessedCallback"));
587             WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
588         }
589         return;
590     }
591
592     if (WKStringIsEqualToUTF8CString(messageName, "QueueBackNavigation")) {
593         ASSERT(WKGetTypeID(messageBody) == WKUInt64GetTypeID());
594         uint64_t stepCount = WKUInt64GetValue(static_cast<WKUInt64Ref>(messageBody));
595         TestController::singleton().workQueueManager().queueBackNavigation(stepCount);
596         return;
597     }
598
599     if (WKStringIsEqualToUTF8CString(messageName, "QueueForwardNavigation")) {
600         ASSERT(WKGetTypeID(messageBody) == WKUInt64GetTypeID());
601         uint64_t stepCount = WKUInt64GetValue(static_cast<WKUInt64Ref>(messageBody));
602         TestController::singleton().workQueueManager().queueForwardNavigation(stepCount);
603         return;
604     }
605
606     if (WKStringIsEqualToUTF8CString(messageName, "QueueLoad")) {
607         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
608         WKDictionaryRef loadDataDictionary = static_cast<WKDictionaryRef>(messageBody);
609
610         WKRetainPtr<WKStringRef> urlKey(AdoptWK, WKStringCreateWithUTF8CString("url"));
611         WKStringRef urlWK = static_cast<WKStringRef>(WKDictionaryGetItemForKey(loadDataDictionary, urlKey.get()));
612
613         WKRetainPtr<WKStringRef> targetKey(AdoptWK, WKStringCreateWithUTF8CString("target"));
614         WKStringRef targetWK = static_cast<WKStringRef>(WKDictionaryGetItemForKey(loadDataDictionary, targetKey.get()));
615
616         WKRetainPtr<WKStringRef> shouldOpenExternalURLsKey(AdoptWK, WKStringCreateWithUTF8CString("shouldOpenExternalURLs"));
617         WKBooleanRef shouldOpenExternalURLsValueWK = static_cast<WKBooleanRef>(WKDictionaryGetItemForKey(loadDataDictionary, shouldOpenExternalURLsKey.get()));
618
619         TestController::singleton().workQueueManager().queueLoad(toWTFString(urlWK), toWTFString(targetWK), WKBooleanGetValue(shouldOpenExternalURLsValueWK));
620         return;
621     }
622
623     if (WKStringIsEqualToUTF8CString(messageName, "QueueLoadHTMLString")) {
624         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
625         WKDictionaryRef loadDataDictionary = static_cast<WKDictionaryRef>(messageBody);
626
627         WKRetainPtr<WKStringRef> contentKey(AdoptWK, WKStringCreateWithUTF8CString("content"));
628         WKStringRef contentWK = static_cast<WKStringRef>(WKDictionaryGetItemForKey(loadDataDictionary, contentKey.get()));
629
630         WKRetainPtr<WKStringRef> baseURLKey(AdoptWK, WKStringCreateWithUTF8CString("baseURL"));
631         WKStringRef baseURLWK = static_cast<WKStringRef>(WKDictionaryGetItemForKey(loadDataDictionary, baseURLKey.get()));
632
633         WKRetainPtr<WKStringRef> unreachableURLKey(AdoptWK, WKStringCreateWithUTF8CString("unreachableURL"));
634         WKStringRef unreachableURLWK = static_cast<WKStringRef>(WKDictionaryGetItemForKey(loadDataDictionary, unreachableURLKey.get()));
635
636         TestController::singleton().workQueueManager().queueLoadHTMLString(toWTFString(contentWK), baseURLWK ? toWTFString(baseURLWK) : String(), unreachableURLWK ? toWTFString(unreachableURLWK) : String());
637         return;
638     }
639
640     if (WKStringIsEqualToUTF8CString(messageName, "QueueReload")) {
641         TestController::singleton().workQueueManager().queueReload();
642         return;
643     }
644
645     if (WKStringIsEqualToUTF8CString(messageName, "QueueLoadingScript")) {
646         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
647         WKStringRef script = static_cast<WKStringRef>(messageBody);
648         TestController::singleton().workQueueManager().queueLoadingScript(toWTFString(script));
649         return;
650     }
651
652     if (WKStringIsEqualToUTF8CString(messageName, "QueueNonLoadingScript")) {
653         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
654         WKStringRef script = static_cast<WKStringRef>(messageBody);
655         TestController::singleton().workQueueManager().queueNonLoadingScript(toWTFString(script));
656         return;
657     }
658
659     if (WKStringIsEqualToUTF8CString(messageName, "SetRejectsProtectionSpaceAndContinueForAuthenticationChallenges")) {
660         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
661         WKBooleanRef value = static_cast<WKBooleanRef>(messageBody);
662         TestController::singleton().setRejectsProtectionSpaceAndContinueForAuthenticationChallenges(WKBooleanGetValue(value));
663         return;
664     }
665
666     if (WKStringIsEqualToUTF8CString(messageName, "SetHandlesAuthenticationChallenges")) {
667         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
668         WKBooleanRef value = static_cast<WKBooleanRef>(messageBody);
669         TestController::singleton().setHandlesAuthenticationChallenges(WKBooleanGetValue(value));
670         return;
671     }
672
673     if (WKStringIsEqualToUTF8CString(messageName, "SetShouldLogCanAuthenticateAgainstProtectionSpace")) {
674         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
675         WKBooleanRef value = static_cast<WKBooleanRef>(messageBody);
676         TestController::singleton().setShouldLogCanAuthenticateAgainstProtectionSpace(WKBooleanGetValue(value));
677         return;
678     }
679
680     if (WKStringIsEqualToUTF8CString(messageName, "SetShouldLogDownloadCallbacks")) {
681         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
682         WKBooleanRef value = static_cast<WKBooleanRef>(messageBody);
683         TestController::singleton().setShouldLogDownloadCallbacks(WKBooleanGetValue(value));
684         return;
685     }
686
687     if (WKStringIsEqualToUTF8CString(messageName, "SetAuthenticationUsername")) {
688         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
689         WKStringRef username = static_cast<WKStringRef>(messageBody);
690         TestController::singleton().setAuthenticationUsername(toWTFString(username));
691         return;
692     }
693
694     if (WKStringIsEqualToUTF8CString(messageName, "SetAuthenticationPassword")) {
695         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
696         WKStringRef password = static_cast<WKStringRef>(messageBody);
697         TestController::singleton().setAuthenticationPassword(toWTFString(password));
698         return;
699     }
700
701     if (WKStringIsEqualToUTF8CString(messageName, "SetBlockAllPlugins")) {
702         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
703         WKBooleanRef shouldBlock = static_cast<WKBooleanRef>(messageBody);
704         TestController::singleton().setBlockAllPlugins(WKBooleanGetValue(shouldBlock));
705         return;
706     }
707
708     if (WKStringIsEqualToUTF8CString(messageName, "SetPluginSupportedMode")) {
709         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
710         WKStringRef mode = static_cast<WKStringRef>(messageBody);
711         TestController::singleton().setPluginSupportedMode(toWTFString(mode));
712         return;
713     }
714
715     if (WKStringIsEqualToUTF8CString(messageName, "SetShouldDecideNavigationPolicyAfterDelay")) {
716         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
717         WKBooleanRef value = static_cast<WKBooleanRef>(messageBody);
718         TestController::singleton().setShouldDecideNavigationPolicyAfterDelay(WKBooleanGetValue(value));
719         return;
720     }
721
722     if (WKStringIsEqualToUTF8CString(messageName, "SetShouldDecideResponsePolicyAfterDelay")) {
723         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
724         WKBooleanRef value = static_cast<WKBooleanRef>(messageBody);
725         TestController::singleton().setShouldDecideResponsePolicyAfterDelay(WKBooleanGetValue(value));
726         return;
727     }
728
729     if (WKStringIsEqualToUTF8CString(messageName, "SetNavigationGesturesEnabled")) {
730         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
731         WKBooleanRef value = static_cast<WKBooleanRef>(messageBody);
732         TestController::singleton().setNavigationGesturesEnabled(WKBooleanGetValue(value));
733         return;
734     }
735     
736     if (WKStringIsEqualToUTF8CString(messageName, "SetIgnoresViewportScaleLimits")) {
737         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
738         WKBooleanRef value = static_cast<WKBooleanRef>(messageBody);
739         TestController::singleton().setIgnoresViewportScaleLimits(WKBooleanGetValue(value));
740         return;
741     }
742
743     if (WKStringIsEqualToUTF8CString(messageName, "SetShouldDownloadUndisplayableMIMETypes")) {
744         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
745         WKBooleanRef value = static_cast<WKBooleanRef>(messageBody);
746         TestController::singleton().setShouldDownloadUndisplayableMIMETypes(WKBooleanGetValue(value));
747         return;
748     }
749
750     if (WKStringIsEqualToUTF8CString(messageName, "SetShouldAllowDeviceOrientationAndMotionAccess")) {
751         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
752         WKBooleanRef value = static_cast<WKBooleanRef>(messageBody);
753         TestController::singleton().setShouldAllowDeviceOrientationAndMotionAccess(WKBooleanGetValue(value));
754         return;
755     }
756
757     if (WKStringIsEqualToUTF8CString(messageName, "RunUIProcessScript")) {
758         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
759         WKRetainPtr<WKStringRef> scriptKey(AdoptWK, WKStringCreateWithUTF8CString("Script"));
760         WKRetainPtr<WKStringRef> callbackIDKey(AdoptWK, WKStringCreateWithUTF8CString("CallbackID"));
761
762         UIScriptInvocationData* invocationData = new UIScriptInvocationData();
763         invocationData->testInvocation = this;
764         invocationData->callbackID = (unsigned)WKUInt64GetValue(static_cast<WKUInt64Ref>(WKDictionaryGetItemForKey(messageBodyDictionary, callbackIDKey.get())));
765         invocationData->scriptString = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, scriptKey.get()));
766         m_pendingUIScriptInvocationData = invocationData;
767         WKPageCallAfterNextPresentationUpdate(TestController::singleton().mainWebView()->page(), invocationData, runUISideScriptAfterUpdateCallback);
768         return;
769     }
770
771     if (WKStringIsEqualToUTF8CString(messageName, "SetOpenPanelFileURLs")) {
772         TestController::singleton().setOpenPanelFileURLs(static_cast<WKArrayRef>(messageBody));
773         return;
774     }
775
776     ASSERT_NOT_REACHED();
777 }
778
779 WKRetainPtr<WKTypeRef> TestInvocation::didReceiveSynchronousMessageFromInjectedBundle(WKStringRef messageName, WKTypeRef messageBody)
780 {
781     if (WKStringIsEqualToUTF8CString(messageName, "Initialization")) {
782         auto settings = createTestSettingsDictionary();
783         WKRetainPtr<WKStringRef> resumeTestingKey = adoptWK(WKStringCreateWithUTF8CString("ResumeTesting"));
784         WKRetainPtr<WKBooleanRef> resumeTestingValue = adoptWK(WKBooleanCreate(m_startedTesting));
785         WKDictionarySetItem(settings.get(), resumeTestingKey.get(), resumeTestingValue.get());
786         return settings;
787     }
788
789     if (WKStringIsEqualToUTF8CString(messageName, "SetDumpPixels")) {
790         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
791         m_dumpPixels = WKBooleanGetValue(static_cast<WKBooleanRef>(messageBody));
792         return nullptr;
793     }
794     if (WKStringIsEqualToUTF8CString(messageName, "GetDumpPixels"))
795         return WKRetainPtr<WKTypeRef>(AdoptWK, WKBooleanCreate(m_dumpPixels));
796
797     if (WKStringIsEqualToUTF8CString(messageName, "SetWhatToDump")) {
798         ASSERT(WKGetTypeID(messageBody) == WKUInt64GetTypeID());
799         m_whatToDump = static_cast<WhatToDump>(WKUInt64GetValue(static_cast<WKUInt64Ref>(messageBody)));
800         return nullptr;
801     }
802     if (WKStringIsEqualToUTF8CString(messageName, "GetWhatToDump"))
803         return WKRetainPtr<WKTypeRef>(AdoptWK, WKUInt64Create(static_cast<uint64_t>(m_whatToDump)));
804
805     if (WKStringIsEqualToUTF8CString(messageName, "SetWaitUntilDone")) {
806         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
807         m_waitUntilDone = static_cast<unsigned char>(WKBooleanGetValue(static_cast<WKBooleanRef>(messageBody)));
808         return nullptr;
809     }
810     if (WKStringIsEqualToUTF8CString(messageName, "GetWaitUntilDone"))
811         return WKRetainPtr<WKTypeRef>(AdoptWK, WKBooleanCreate(m_waitUntilDone));
812
813     if (WKStringIsEqualToUTF8CString(messageName, "SetDumpFrameLoadCallbacks")) {
814         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
815         m_dumpFrameLoadCallbacks = static_cast<unsigned char>(WKBooleanGetValue(static_cast<WKBooleanRef>(messageBody)));
816         return nullptr;
817     }
818     if (WKStringIsEqualToUTF8CString(messageName, "GetDumpFrameLoadCallbacks"))
819         return WKRetainPtr<WKTypeRef>(AdoptWK, WKBooleanCreate(m_dumpFrameLoadCallbacks));
820
821     if (WKStringIsEqualToUTF8CString(messageName, "SetCanOpenWindows")) {
822         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
823         m_canOpenWindows = static_cast<unsigned char>(WKBooleanGetValue(static_cast<WKBooleanRef>(messageBody)));
824         return nullptr;
825     }
826
827     if (WKStringIsEqualToUTF8CString(messageName, "SetWindowIsKey")) {
828         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
829         WKBooleanRef isKeyValue = static_cast<WKBooleanRef>(messageBody);
830         TestController::singleton().mainWebView()->setWindowIsKey(WKBooleanGetValue(isKeyValue));
831         return nullptr;
832     }
833
834     if (WKStringIsEqualToUTF8CString(messageName, "SetViewSize")) {
835         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
836
837         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
838         WKRetainPtr<WKStringRef> widthKey(AdoptWK, WKStringCreateWithUTF8CString("width"));
839         WKRetainPtr<WKStringRef> heightKey(AdoptWK, WKStringCreateWithUTF8CString("height"));
840
841         WKDoubleRef widthWK = static_cast<WKDoubleRef>(WKDictionaryGetItemForKey(messageBodyDictionary, widthKey.get()));
842         WKDoubleRef heightWK = static_cast<WKDoubleRef>(WKDictionaryGetItemForKey(messageBodyDictionary, heightKey.get()));
843
844         TestController::singleton().mainWebView()->resizeTo(WKDoubleGetValue(widthWK), WKDoubleGetValue(heightWK));
845         return nullptr;
846     }
847
848     if (WKStringIsEqualToUTF8CString(messageName, "IsGeolocationClientActive")) {
849         bool isActive = TestController::singleton().isGeolocationProviderActive();
850         WKRetainPtr<WKTypeRef> result(AdoptWK, WKBooleanCreate(isActive));
851         return result;
852     }
853
854     if (WKStringIsEqualToUTF8CString(messageName, "IsWorkQueueEmpty")) {
855         bool isEmpty = TestController::singleton().workQueueManager().isWorkQueueEmpty();
856         WKRetainPtr<WKTypeRef> result(AdoptWK, WKBooleanCreate(isEmpty));
857         return result;
858     }
859
860     if (WKStringIsEqualToUTF8CString(messageName, "DidReceiveServerRedirectForProvisionalNavigation")) {
861         WKRetainPtr<WKBooleanRef> result(AdoptWK, WKBooleanCreate(TestController::singleton().didReceiveServerRedirectForProvisionalNavigation()));
862         return result;
863     }
864
865     if (WKStringIsEqualToUTF8CString(messageName, "ClearDidReceiveServerRedirectForProvisionalNavigation")) {
866         TestController::singleton().clearDidReceiveServerRedirectForProvisionalNavigation();
867         return nullptr;
868     }
869
870     if (WKStringIsEqualToUTF8CString(messageName, "SecureEventInputIsEnabled")) {
871 #if PLATFORM(MAC) && !PLATFORM(IOS_FAMILY)
872         WKRetainPtr<WKBooleanRef> result(AdoptWK, WKBooleanCreate(IsSecureEventInputEnabled()));
873 #else
874         WKRetainPtr<WKBooleanRef> result(AdoptWK, WKBooleanCreate(false));
875 #endif
876         return result;
877     }
878
879     if (WKStringIsEqualToUTF8CString(messageName, "SetAlwaysAcceptCookies")) {
880         WKBooleanRef accept = static_cast<WKBooleanRef>(messageBody);
881         WKHTTPCookieAcceptPolicy policy = WKBooleanGetValue(accept) ? kWKHTTPCookieAcceptPolicyAlways : kWKHTTPCookieAcceptPolicyOnlyFromMainDocumentDomain;
882         // FIXME: This updates the policy in WebProcess and in NetworkProcess asynchronously, which might break some tests' expectations.
883         WKCookieManagerSetHTTPCookieAcceptPolicy(WKContextGetCookieManager(TestController::singleton().context()), policy);
884         return nullptr;
885     }
886
887     if (WKStringIsEqualToUTF8CString(messageName, "SetOnlyAcceptFirstPartyCookies")) {
888         WKBooleanRef accept = static_cast<WKBooleanRef>(messageBody);
889         WKHTTPCookieAcceptPolicy policy = WKBooleanGetValue(accept) ? kWKHTTPCookieAcceptPolicyExclusivelyFromMainDocumentDomain : kWKHTTPCookieAcceptPolicyOnlyFromMainDocumentDomain;
890         // FIXME: This updates the policy in WebProcess and in NetworkProcess asynchronously, which might break some tests' expectations.
891         WKCookieManagerSetHTTPCookieAcceptPolicy(WKContextGetCookieManager(TestController::singleton().context()), policy);
892         return nullptr;
893     }
894     
895     if (WKStringIsEqualToUTF8CString(messageName, "SetCustomUserAgent")) {
896         WKStringRef userAgent = static_cast<WKStringRef>(messageBody);
897         WKPageSetCustomUserAgent(TestController::singleton().mainWebView()->page(), userAgent);
898         return nullptr;
899     }
900
901     if (WKStringIsEqualToUTF8CString(messageName, "SetStorageAccessAPIEnabled")) {
902         WKBooleanRef accept = static_cast<WKBooleanRef>(messageBody);
903         WKCookieManagerSetStorageAccessAPIEnabled(WKContextGetCookieManager(TestController::singleton().context()), WKBooleanGetValue(accept));
904         return nullptr;
905     }
906
907     if (WKStringIsEqualToUTF8CString(messageName, "GetAllStorageAccessEntries")) {
908         TestController::singleton().getAllStorageAccessEntries();
909         return nullptr;
910     }
911
912     if (WKStringIsEqualToUTF8CString(messageName, "SetAllowsAnySSLCertificate")) {
913         TestController::singleton().setAllowsAnySSLCertificate(WKBooleanGetValue(static_cast<WKBooleanRef>(messageBody)));
914         return nullptr;
915     }
916
917     if (WKStringIsEqualToUTF8CString(messageName, "ImageCountInGeneralPasteboard")) {
918         unsigned count = TestController::singleton().imageCountInGeneralPasteboard();
919         WKRetainPtr<WKUInt64Ref> result(AdoptWK, WKUInt64Create(count));
920         return result;
921     }
922     
923     if (WKStringIsEqualToUTF8CString(messageName, "DeleteAllIndexedDatabases")) {
924         WKWebsiteDataStoreRemoveAllIndexedDatabases(WKContextGetWebsiteDataStore(TestController::singleton().context()), nullptr, { });
925         return nullptr;
926     }
927
928     if (WKStringIsEqualToUTF8CString(messageName, "AddMockMediaDevice")) {
929         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
930
931         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
932         WKRetainPtr<WKStringRef> persistentIDKey(AdoptWK, WKStringCreateWithUTF8CString("PersistentID"));
933         WKRetainPtr<WKStringRef> labelKey(AdoptWK, WKStringCreateWithUTF8CString("Label"));
934         WKRetainPtr<WKStringRef> typeKey(AdoptWK, WKStringCreateWithUTF8CString("Type"));
935
936         auto persistentID = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, persistentIDKey.get()));
937         auto label = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, labelKey.get()));
938         auto type = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, typeKey.get()));
939
940         TestController::singleton().addMockMediaDevice(persistentID, label, type);
941         return nullptr;
942     }
943
944     if (WKStringIsEqualToUTF8CString(messageName, "ClearMockMediaDevices")) {
945         TestController::singleton().clearMockMediaDevices();
946         return nullptr;
947     }
948
949     if (WKStringIsEqualToUTF8CString(messageName, "RemoveMockMediaDevice")) {
950         WKStringRef persistentId = static_cast<WKStringRef>(messageBody);
951
952         TestController::singleton().removeMockMediaDevice(persistentId);
953         return nullptr;
954     }
955
956     if (WKStringIsEqualToUTF8CString(messageName, "ResetMockMediaDevices")) {
957         TestController::singleton().resetMockMediaDevices();
958         return nullptr;
959     }
960
961 #if PLATFORM(MAC)
962     if (WKStringIsEqualToUTF8CString(messageName, "ConnectMockGamepad")) {
963         ASSERT(WKGetTypeID(messageBody) == WKUInt64GetTypeID());
964
965         uint64_t index = WKUInt64GetValue(static_cast<WKUInt64Ref>(messageBody));
966         WebCoreTestSupport::connectMockGamepad(index);
967         
968         return nullptr;
969     }
970
971     if (WKStringIsEqualToUTF8CString(messageName, "DisconnectMockGamepad")) {
972         ASSERT(WKGetTypeID(messageBody) == WKUInt64GetTypeID());
973
974         uint64_t index = WKUInt64GetValue(static_cast<WKUInt64Ref>(messageBody));
975         WebCoreTestSupport::disconnectMockGamepad(index);
976
977         return nullptr;
978     }
979
980     if (WKStringIsEqualToUTF8CString(messageName, "SetMockGamepadDetails")) {
981         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
982
983         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
984         WKRetainPtr<WKStringRef> gamepadIndexKey(AdoptWK, WKStringCreateWithUTF8CString("GamepadIndex"));
985         WKRetainPtr<WKStringRef> gamepadIDKey(AdoptWK, WKStringCreateWithUTF8CString("GamepadID"));
986         WKRetainPtr<WKStringRef> axisCountKey(AdoptWK, WKStringCreateWithUTF8CString("AxisCount"));
987         WKRetainPtr<WKStringRef> buttonCountKey(AdoptWK, WKStringCreateWithUTF8CString("ButtonCount"));
988
989         WKUInt64Ref gamepadIndex = static_cast<WKUInt64Ref>(WKDictionaryGetItemForKey(messageBodyDictionary, gamepadIndexKey.get()));
990         WKStringRef gamepadID = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, gamepadIDKey.get()));
991         WKUInt64Ref axisCount = static_cast<WKUInt64Ref>(WKDictionaryGetItemForKey(messageBodyDictionary, axisCountKey.get()));
992         WKUInt64Ref buttonCount = static_cast<WKUInt64Ref>(WKDictionaryGetItemForKey(messageBodyDictionary, buttonCountKey.get()));
993
994         WebCoreTestSupport::setMockGamepadDetails(WKUInt64GetValue(gamepadIndex), toWTFString(gamepadID), WKUInt64GetValue(axisCount), WKUInt64GetValue(buttonCount));
995         return nullptr;
996     }
997
998     if (WKStringIsEqualToUTF8CString(messageName, "SetMockGamepadAxisValue")) {
999         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
1000
1001         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
1002         WKRetainPtr<WKStringRef> gamepadIndexKey(AdoptWK, WKStringCreateWithUTF8CString("GamepadIndex"));
1003         WKRetainPtr<WKStringRef> axisIndexKey(AdoptWK, WKStringCreateWithUTF8CString("AxisIndex"));
1004         WKRetainPtr<WKStringRef> valueKey(AdoptWK, WKStringCreateWithUTF8CString("Value"));
1005
1006         WKUInt64Ref gamepadIndex = static_cast<WKUInt64Ref>(WKDictionaryGetItemForKey(messageBodyDictionary, gamepadIndexKey.get()));
1007         WKUInt64Ref axisIndex = static_cast<WKUInt64Ref>(WKDictionaryGetItemForKey(messageBodyDictionary, axisIndexKey.get()));
1008         WKDoubleRef value = static_cast<WKDoubleRef>(WKDictionaryGetItemForKey(messageBodyDictionary, valueKey.get()));
1009
1010         WebCoreTestSupport::setMockGamepadAxisValue(WKUInt64GetValue(gamepadIndex), WKUInt64GetValue(axisIndex), WKDoubleGetValue(value));
1011
1012         return nullptr;
1013     }
1014
1015     if (WKStringIsEqualToUTF8CString(messageName, "SetMockGamepadButtonValue")) {
1016         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
1017
1018         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
1019         WKRetainPtr<WKStringRef> gamepadIndexKey(AdoptWK, WKStringCreateWithUTF8CString("GamepadIndex"));
1020         WKRetainPtr<WKStringRef> buttonIndexKey(AdoptWK, WKStringCreateWithUTF8CString("ButtonIndex"));
1021         WKRetainPtr<WKStringRef> valueKey(AdoptWK, WKStringCreateWithUTF8CString("Value"));
1022
1023         WKUInt64Ref gamepadIndex = static_cast<WKUInt64Ref>(WKDictionaryGetItemForKey(messageBodyDictionary, gamepadIndexKey.get()));
1024         WKUInt64Ref buttonIndex = static_cast<WKUInt64Ref>(WKDictionaryGetItemForKey(messageBodyDictionary, buttonIndexKey.get()));
1025         WKDoubleRef value = static_cast<WKDoubleRef>(WKDictionaryGetItemForKey(messageBodyDictionary, valueKey.get()));
1026
1027         WebCoreTestSupport::setMockGamepadButtonValue(WKUInt64GetValue(gamepadIndex), WKUInt64GetValue(buttonIndex), WKDoubleGetValue(value));
1028
1029         return nullptr;
1030     }
1031 #endif // PLATFORM(MAC)
1032
1033     if (WKStringIsEqualToUTF8CString(messageName, "UserMediaPermissionRequestCountForOrigin")) {
1034         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
1035         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
1036
1037         WKRetainPtr<WKStringRef> originKey(AdoptWK, WKStringCreateWithUTF8CString("origin"));
1038         WKStringRef originWK = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, originKey.get()));
1039
1040         WKRetainPtr<WKStringRef> parentOriginKey(AdoptWK, WKStringCreateWithUTF8CString("parentOrigin"));
1041         WKStringRef parentOriginWK = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, parentOriginKey.get()));
1042         
1043         unsigned count = TestController::singleton().userMediaPermissionRequestCountForOrigin(originWK, parentOriginWK);
1044         WKRetainPtr<WKUInt64Ref> result(AdoptWK, WKUInt64Create(count));
1045         return result;
1046     }
1047     if (WKStringIsEqualToUTF8CString(messageName, "IsDoingMediaCapture")) {
1048         WKRetainPtr<WKTypeRef> result(AdoptWK, WKBooleanCreate(TestController::singleton().isDoingMediaCapture()));
1049         return result;
1050     }
1051
1052     if (WKStringIsEqualToUTF8CString(messageName, "SetStatisticsDebugMode")) {
1053         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
1054         WKBooleanRef value = static_cast<WKBooleanRef>(messageBody);
1055         TestController::singleton().setStatisticsDebugMode(WKBooleanGetValue(value));
1056         return nullptr;
1057     }
1058     
1059     if (WKStringIsEqualToUTF8CString(messageName, "SetStatisticsPrevalentResourceForDebugMode")) {
1060         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
1061         WKStringRef hostName = static_cast<WKStringRef>(messageBody);
1062         TestController::singleton().setStatisticsPrevalentResourceForDebugMode(hostName);
1063         return nullptr;
1064     }
1065     
1066     if (WKStringIsEqualToUTF8CString(messageName, "SetStatisticsLastSeen")) {
1067         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
1068         
1069         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
1070         WKRetainPtr<WKStringRef> hostNameKey(AdoptWK, WKStringCreateWithUTF8CString("HostName"));
1071         WKRetainPtr<WKStringRef> valueKey(AdoptWK, WKStringCreateWithUTF8CString("Value"));
1072         
1073         WKStringRef hostName = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, hostNameKey.get()));
1074         WKDoubleRef value = static_cast<WKDoubleRef>(WKDictionaryGetItemForKey(messageBodyDictionary, valueKey.get()));
1075         
1076         TestController::singleton().setStatisticsLastSeen(hostName, WKDoubleGetValue(value));
1077         
1078         return nullptr;
1079     }
1080     
1081     if (WKStringIsEqualToUTF8CString(messageName, "SetStatisticsPrevalentResource")) {
1082         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
1083
1084         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
1085         WKRetainPtr<WKStringRef> hostNameKey(AdoptWK, WKStringCreateWithUTF8CString("HostName"));
1086         WKRetainPtr<WKStringRef> valueKey(AdoptWK, WKStringCreateWithUTF8CString("Value"));
1087
1088         WKStringRef hostName = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, hostNameKey.get()));
1089         WKBooleanRef value = static_cast<WKBooleanRef>(WKDictionaryGetItemForKey(messageBodyDictionary, valueKey.get()));
1090
1091         TestController::singleton().setStatisticsPrevalentResource(hostName, WKBooleanGetValue(value));
1092         return nullptr;
1093     }
1094
1095     if (WKStringIsEqualToUTF8CString(messageName, "SetStatisticsVeryPrevalentResource")) {
1096         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
1097         
1098         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
1099         WKRetainPtr<WKStringRef> hostNameKey(AdoptWK, WKStringCreateWithUTF8CString("HostName"));
1100         WKRetainPtr<WKStringRef> valueKey(AdoptWK, WKStringCreateWithUTF8CString("Value"));
1101         
1102         WKStringRef hostName = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, hostNameKey.get()));
1103         WKBooleanRef value = static_cast<WKBooleanRef>(WKDictionaryGetItemForKey(messageBodyDictionary, valueKey.get()));
1104         
1105         TestController::singleton().setStatisticsVeryPrevalentResource(hostName, WKBooleanGetValue(value));
1106         return nullptr;
1107     }
1108     
1109     if (WKStringIsEqualToUTF8CString(messageName, "dumpResourceLoadStatistics")) {
1110         dumpResourceLoadStatistics();
1111         return nullptr;
1112     }
1113
1114     if (WKStringIsEqualToUTF8CString(messageName, "IsStatisticsPrevalentResource")) {
1115         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
1116
1117         WKStringRef hostName = static_cast<WKStringRef>(messageBody);
1118         bool isPrevalent = TestController::singleton().isStatisticsPrevalentResource(hostName);
1119         WKRetainPtr<WKTypeRef> result(AdoptWK, WKBooleanCreate(isPrevalent));
1120         return result;
1121     }
1122
1123     if (WKStringIsEqualToUTF8CString(messageName, "IsStatisticsVeryPrevalentResource")) {
1124         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
1125         
1126         WKStringRef hostName = static_cast<WKStringRef>(messageBody);
1127         bool isPrevalent = TestController::singleton().isStatisticsVeryPrevalentResource(hostName);
1128         WKRetainPtr<WKTypeRef> result(AdoptWK, WKBooleanCreate(isPrevalent));
1129         return result;
1130     }
1131     
1132     if (WKStringIsEqualToUTF8CString(messageName, "IsStatisticsRegisteredAsSubresourceUnder")) {
1133         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
1134         
1135         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
1136         WKRetainPtr<WKStringRef> subresourceHostKey(AdoptWK, WKStringCreateWithUTF8CString("SubresourceHost"));
1137         WKRetainPtr<WKStringRef> topFrameHostKey(AdoptWK, WKStringCreateWithUTF8CString("TopFrameHost"));
1138         
1139         WKStringRef subresourceHost = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, subresourceHostKey.get()));
1140         WKStringRef topFrameHost = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, topFrameHostKey.get()));
1141         
1142         bool isRegisteredAsSubresourceUnder = TestController::singleton().isStatisticsRegisteredAsSubresourceUnder(subresourceHost, topFrameHost);
1143         WKRetainPtr<WKTypeRef> result(AdoptWK, WKBooleanCreate(isRegisteredAsSubresourceUnder));
1144         return result;
1145     }
1146     
1147     if (WKStringIsEqualToUTF8CString(messageName, "IsStatisticsRegisteredAsSubFrameUnder")) {
1148         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
1149         
1150         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
1151         WKRetainPtr<WKStringRef> subFrameHostKey(AdoptWK, WKStringCreateWithUTF8CString("SubFrameHost"));
1152         WKRetainPtr<WKStringRef> topFrameHostKey(AdoptWK, WKStringCreateWithUTF8CString("TopFrameHost"));
1153         
1154         WKStringRef subFrameHost = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, subFrameHostKey.get()));
1155         WKStringRef topFrameHost = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, topFrameHostKey.get()));
1156
1157         bool isRegisteredAsSubFrameUnder = TestController::singleton().isStatisticsRegisteredAsSubFrameUnder(subFrameHost, topFrameHost);
1158         WKRetainPtr<WKTypeRef> result(AdoptWK, WKBooleanCreate(isRegisteredAsSubFrameUnder));
1159         return result;
1160     }
1161     
1162     if (WKStringIsEqualToUTF8CString(messageName, "IsStatisticsRegisteredAsRedirectingTo")) {
1163         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
1164         
1165         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
1166         WKRetainPtr<WKStringRef> hostRedirectedFromKey(AdoptWK, WKStringCreateWithUTF8CString("HostRedirectedFrom"));
1167         WKRetainPtr<WKStringRef> hostRedirectedToKey(AdoptWK, WKStringCreateWithUTF8CString("HostRedirectedTo"));
1168         
1169         WKStringRef hostRedirectedFrom = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, hostRedirectedFromKey.get()));
1170         WKStringRef hostRedirectedTo = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, hostRedirectedToKey.get()));
1171         
1172         bool isRegisteredAsRedirectingTo = TestController::singleton().isStatisticsRegisteredAsRedirectingTo(hostRedirectedFrom, hostRedirectedTo);
1173         WKRetainPtr<WKTypeRef> result(AdoptWK, WKBooleanCreate(isRegisteredAsRedirectingTo));
1174         return result;
1175     }
1176     
1177     if (WKStringIsEqualToUTF8CString(messageName, "SetStatisticsHasHadUserInteraction")) {
1178         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
1179         
1180         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
1181         WKRetainPtr<WKStringRef> hostNameKey(AdoptWK, WKStringCreateWithUTF8CString("HostName"));
1182         WKRetainPtr<WKStringRef> valueKey(AdoptWK, WKStringCreateWithUTF8CString("Value"));
1183         
1184         WKStringRef hostName = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, hostNameKey.get()));
1185         WKBooleanRef value = static_cast<WKBooleanRef>(WKDictionaryGetItemForKey(messageBodyDictionary, valueKey.get()));
1186         
1187         TestController::singleton().setStatisticsHasHadUserInteraction(hostName, WKBooleanGetValue(value));
1188         return nullptr;
1189     }
1190
1191     if (WKStringIsEqualToUTF8CString(messageName, "IsStatisticsHasHadUserInteraction")) {
1192         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
1193         
1194         WKStringRef hostName = static_cast<WKStringRef>(messageBody);
1195         bool hasHadUserInteraction = TestController::singleton().isStatisticsHasHadUserInteraction(hostName);
1196         WKRetainPtr<WKTypeRef> result(AdoptWK, WKBooleanCreate(hasHadUserInteraction));
1197         return result;
1198     }
1199     
1200     if (WKStringIsEqualToUTF8CString(messageName, "SetStatisticsGrandfathered")) {
1201         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
1202         
1203         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
1204         WKRetainPtr<WKStringRef> hostNameKey(AdoptWK, WKStringCreateWithUTF8CString("HostName"));
1205         WKRetainPtr<WKStringRef> valueKey(AdoptWK, WKStringCreateWithUTF8CString("Value"));
1206         
1207         WKStringRef hostName = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, hostNameKey.get()));
1208         WKBooleanRef value = static_cast<WKBooleanRef>(WKDictionaryGetItemForKey(messageBodyDictionary, valueKey.get()));
1209         
1210         TestController::singleton().setStatisticsGrandfathered(hostName, WKBooleanGetValue(value));
1211         return nullptr;
1212     }
1213     
1214     if (WKStringIsEqualToUTF8CString(messageName, "IsStatisticsGrandfathered")) {
1215         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
1216         
1217         WKStringRef hostName = static_cast<WKStringRef>(messageBody);
1218         bool isGrandfathered = TestController::singleton().isStatisticsGrandfathered(hostName);
1219         WKRetainPtr<WKTypeRef> result(AdoptWK, WKBooleanCreate(isGrandfathered));
1220         return result;
1221     }
1222     
1223     if (WKStringIsEqualToUTF8CString(messageName, "SetStatisticsSubframeUnderTopFrameOrigin")) {
1224         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
1225         
1226         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
1227         WKRetainPtr<WKStringRef> hostNameKey(AdoptWK, WKStringCreateWithUTF8CString("HostName"));
1228         WKRetainPtr<WKStringRef> topFrameHostNameKey(AdoptWK, WKStringCreateWithUTF8CString("TopFrameHostName"));
1229         
1230         WKStringRef hostName = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, hostNameKey.get()));
1231         WKStringRef topFrameHostName = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, topFrameHostNameKey.get()));
1232
1233         TestController::singleton().setStatisticsSubframeUnderTopFrameOrigin(hostName, topFrameHostName);
1234         return nullptr;
1235     }
1236     
1237     if (WKStringIsEqualToUTF8CString(messageName, "SetStatisticsSubresourceUnderTopFrameOrigin")) {
1238         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
1239         
1240         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
1241         WKRetainPtr<WKStringRef> hostNameKey(AdoptWK, WKStringCreateWithUTF8CString("HostName"));
1242         WKRetainPtr<WKStringRef> topFrameHostNameKey(AdoptWK, WKStringCreateWithUTF8CString("TopFrameHostName"));
1243         
1244         WKStringRef hostName = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, hostNameKey.get()));
1245         WKStringRef topFrameHostName = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, topFrameHostNameKey.get()));
1246         
1247         TestController::singleton().setStatisticsSubresourceUnderTopFrameOrigin(hostName, topFrameHostName);
1248         return nullptr;
1249     }
1250     
1251     if (WKStringIsEqualToUTF8CString(messageName, "SetStatisticsSubresourceUniqueRedirectTo")) {
1252         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
1253         
1254         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
1255         WKRetainPtr<WKStringRef> hostNameKey(AdoptWK, WKStringCreateWithUTF8CString("HostName"));
1256         WKRetainPtr<WKStringRef> hostNameRedirectedToKey(AdoptWK, WKStringCreateWithUTF8CString("HostNameRedirectedTo"));
1257         
1258         WKStringRef hostName = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, hostNameKey.get()));
1259         WKStringRef hostNameRedirectedTo = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, hostNameRedirectedToKey.get()));
1260         
1261         TestController::singleton().setStatisticsSubresourceUniqueRedirectTo(hostName, hostNameRedirectedTo);
1262         return nullptr;
1263     }
1264
1265     if (WKStringIsEqualToUTF8CString(messageName, "SetStatisticsSubresourceUniqueRedirectFrom")) {
1266         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
1267         
1268         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
1269         WKRetainPtr<WKStringRef> hostNameKey(AdoptWK, WKStringCreateWithUTF8CString("HostName"));
1270         WKRetainPtr<WKStringRef> hostNameRedirectedFromKey(AdoptWK, WKStringCreateWithUTF8CString("HostNameRedirectedFrom"));
1271         
1272         WKStringRef hostName = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, hostNameKey.get()));
1273         WKStringRef hostNameRedirectedFrom = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, hostNameRedirectedFromKey.get()));
1274         
1275         TestController::singleton().setStatisticsSubresourceUniqueRedirectFrom(hostName, hostNameRedirectedFrom);
1276         return nullptr;
1277     }
1278     
1279     if (WKStringIsEqualToUTF8CString(messageName, "SetStatisticsTopFrameUniqueRedirectTo")) {
1280         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
1281         
1282         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
1283         WKRetainPtr<WKStringRef> hostNameKey(AdoptWK, WKStringCreateWithUTF8CString("HostName"));
1284         WKRetainPtr<WKStringRef> hostNameRedirectedToKey(AdoptWK, WKStringCreateWithUTF8CString("HostNameRedirectedTo"));
1285         
1286         WKStringRef hostName = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, hostNameKey.get()));
1287         WKStringRef hostNameRedirectedTo = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, hostNameRedirectedToKey.get()));
1288         
1289         TestController::singleton().setStatisticsTopFrameUniqueRedirectTo(hostName, hostNameRedirectedTo);
1290         return nullptr;
1291     }
1292     
1293     if (WKStringIsEqualToUTF8CString(messageName, "SetStatisticsTopFrameUniqueRedirectFrom")) {
1294         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
1295         
1296         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
1297         WKRetainPtr<WKStringRef> hostNameKey(AdoptWK, WKStringCreateWithUTF8CString("HostName"));
1298         WKRetainPtr<WKStringRef> hostNameRedirectedFromKey(AdoptWK, WKStringCreateWithUTF8CString("HostNameRedirectedFrom"));
1299         
1300         WKStringRef hostName = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, hostNameKey.get()));
1301         WKStringRef hostNameRedirectedFrom = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, hostNameRedirectedFromKey.get()));
1302         
1303         TestController::singleton().setStatisticsTopFrameUniqueRedirectFrom(hostName, hostNameRedirectedFrom);
1304         return nullptr;
1305     }
1306     
1307     if (WKStringIsEqualToUTF8CString(messageName, "SetStatisticsTimeToLiveUserInteraction")) {
1308         ASSERT(WKGetTypeID(messageBody) == WKDoubleGetTypeID());
1309         WKDoubleRef seconds = static_cast<WKDoubleRef>(messageBody);
1310         TestController::singleton().setStatisticsTimeToLiveUserInteraction(WKDoubleGetValue(seconds));
1311         return nullptr;
1312     }
1313     
1314     if (WKStringIsEqualToUTF8CString(messageName, "StatisticsProcessStatisticsAndDataRecords")) {
1315         TestController::singleton().statisticsProcessStatisticsAndDataRecords();
1316         return nullptr;
1317     }
1318     
1319     if (WKStringIsEqualToUTF8CString(messageName, "StatisticsUpdateCookieBlocking")) {
1320         TestController::singleton().statisticsUpdateCookieBlocking();
1321         return nullptr;
1322     }
1323
1324     if (WKStringIsEqualToUTF8CString(messageName, "StatisticsSubmitTelemetry")) {
1325         TestController::singleton().statisticsSubmitTelemetry();
1326         return nullptr;
1327     }
1328     
1329     if (WKStringIsEqualToUTF8CString(messageName, "StatisticsNotifyPagesWhenDataRecordsWereScanned")) {
1330         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
1331         WKBooleanRef value = static_cast<WKBooleanRef>(messageBody);
1332         TestController::singleton().setStatisticsNotifyPagesWhenDataRecordsWereScanned(WKBooleanGetValue(value));
1333         return nullptr;
1334     }
1335
1336     if (WKStringIsEqualToUTF8CString(messageName, "StatisticsNotifyPagesWhenTelemetryWasCaptured")) {
1337         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
1338         WKBooleanRef value = static_cast<WKBooleanRef>(messageBody);
1339         TestController::singleton().setStatisticsNotifyPagesWhenTelemetryWasCaptured(WKBooleanGetValue(value));
1340         return nullptr;
1341     }
1342     
1343     if (WKStringIsEqualToUTF8CString(messageName, "StatisticsShouldClassifyResourcesBeforeDataRecordsRemoval")) {
1344         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
1345         WKBooleanRef value = static_cast<WKBooleanRef>(messageBody);
1346         TestController::singleton().setStatisticsShouldClassifyResourcesBeforeDataRecordsRemoval(WKBooleanGetValue(value));
1347         return nullptr;
1348     }
1349
1350     if (WKStringIsEqualToUTF8CString(messageName, "SetStatisticsMinimumTimeBetweenDataRecordsRemoval")) {
1351         ASSERT(WKGetTypeID(messageBody) == WKDoubleGetTypeID());
1352         WKDoubleRef seconds = static_cast<WKDoubleRef>(messageBody);
1353         TestController::singleton().setStatisticsMinimumTimeBetweenDataRecordsRemoval(WKDoubleGetValue(seconds));
1354         return nullptr;
1355     }
1356     
1357     if (WKStringIsEqualToUTF8CString(messageName, "SetStatisticsGrandfatheringTime")) {
1358         ASSERT(WKGetTypeID(messageBody) == WKDoubleGetTypeID());
1359         WKDoubleRef seconds = static_cast<WKDoubleRef>(messageBody);
1360         TestController::singleton().setStatisticsGrandfatheringTime(WKDoubleGetValue(seconds));
1361         return nullptr;
1362     }
1363     
1364     if (WKStringIsEqualToUTF8CString(messageName, "SetMaxStatisticsEntries")) {
1365         ASSERT(WKGetTypeID(messageBody) == WKUInt64GetTypeID());
1366         WKUInt64Ref entries = static_cast<WKUInt64Ref>(messageBody);
1367         TestController::singleton().setStatisticsMaxStatisticsEntries(WKUInt64GetValue(entries));
1368         return nullptr;
1369     }
1370     
1371     if (WKStringIsEqualToUTF8CString(messageName, "SetPruneEntriesDownTo")) {
1372         ASSERT(WKGetTypeID(messageBody) == WKUInt64GetTypeID());
1373         WKUInt64Ref entries = static_cast<WKUInt64Ref>(messageBody);
1374         TestController::singleton().setStatisticsPruneEntriesDownTo(WKUInt64GetValue(entries));
1375         return nullptr;
1376     }
1377     
1378     if (WKStringIsEqualToUTF8CString(messageName, "StatisticsClearInMemoryAndPersistentStore")) {
1379         TestController::singleton().statisticsClearInMemoryAndPersistentStore();
1380         return nullptr;
1381     }
1382     
1383     if (WKStringIsEqualToUTF8CString(messageName, "StatisticsClearInMemoryAndPersistentStoreModifiedSinceHours")) {
1384         ASSERT(WKGetTypeID(messageBody) == WKUInt64GetTypeID());
1385         WKUInt64Ref hours = static_cast<WKUInt64Ref>(messageBody);
1386         TestController::singleton().statisticsClearInMemoryAndPersistentStoreModifiedSinceHours(WKUInt64GetValue(hours));
1387         return nullptr;
1388     }
1389     
1390     if (WKStringIsEqualToUTF8CString(messageName, "StatisticsClearThroughWebsiteDataRemoval")) {
1391         TestController::singleton().statisticsClearThroughWebsiteDataRemoval();
1392         return nullptr;
1393     }
1394
1395     if (WKStringIsEqualToUTF8CString(messageName, "StatisticsDeleteCookiesForHost")) {
1396         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
1397         
1398         WKDictionaryRef messageBodyDictionary = static_cast<WKDictionaryRef>(messageBody);
1399         WKRetainPtr<WKStringRef> hostNameKey(AdoptWK, WKStringCreateWithUTF8CString("HostName"));
1400         WKRetainPtr<WKStringRef> valueKey(AdoptWK, WKStringCreateWithUTF8CString("IncludeHttpOnlyCookies"));
1401         
1402         WKStringRef hostName = static_cast<WKStringRef>(WKDictionaryGetItemForKey(messageBodyDictionary, hostNameKey.get()));
1403         WKBooleanRef includeHttpOnlyCookies = static_cast<WKBooleanRef>(WKDictionaryGetItemForKey(messageBodyDictionary, valueKey.get()));
1404         
1405         TestController::singleton().statisticsDeleteCookiesForHost(hostName, WKBooleanGetValue(includeHttpOnlyCookies));
1406         return nullptr;
1407     }
1408
1409     if (WKStringIsEqualToUTF8CString(messageName, "SetStatisticsCacheMaxAgeCap")) {
1410         ASSERT(WKGetTypeID(messageBody) == WKDoubleGetTypeID());
1411         WKDoubleRef seconds = static_cast<WKDoubleRef>(messageBody);
1412         TestController::singleton().setStatisticsCacheMaxAgeCap(WKDoubleGetValue(seconds));
1413         return nullptr;
1414     }
1415
1416     if (WKStringIsEqualToUTF8CString(messageName, "StatisticsResetToConsistentState")) {
1417         if (m_shouldDumpResourceLoadStatistics)
1418             m_savedResourceLoadStatistics = TestController::singleton().dumpResourceLoadStatistics();
1419         TestController::singleton().statisticsResetToConsistentState();
1420         return nullptr;
1421     }
1422
1423     if (WKStringIsEqualToUTF8CString(messageName, "RemoveAllSessionCredentials")) {
1424         TestController::singleton().removeAllSessionCredentials();
1425         return nullptr;
1426     }
1427
1428     if (WKStringIsEqualToUTF8CString(messageName, "ClearDOMCache")) {
1429         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
1430         WKStringRef origin = static_cast<WKStringRef>(messageBody);
1431
1432         TestController::singleton().clearDOMCache(origin);
1433         return nullptr;
1434     }
1435
1436     if (WKStringIsEqualToUTF8CString(messageName, "ClearDOMCaches")) {
1437         TestController::singleton().clearDOMCaches();
1438         return nullptr;
1439     }
1440
1441     if (WKStringIsEqualToUTF8CString(messageName, "HasDOMCache")) {
1442         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
1443         WKStringRef origin = static_cast<WKStringRef>(messageBody);
1444
1445         bool hasDOMCache = TestController::singleton().hasDOMCache(origin);
1446         WKRetainPtr<WKTypeRef> result(AdoptWK, WKBooleanCreate(hasDOMCache));
1447         return result;
1448     }
1449
1450     if (WKStringIsEqualToUTF8CString(messageName, "DOMCacheSize")) {
1451         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
1452         WKStringRef origin = static_cast<WKStringRef>(messageBody);
1453
1454         auto domCacheSize = TestController::singleton().domCacheSize(origin);
1455         WKRetainPtr<WKTypeRef> result(AdoptWK, WKUInt64Create(domCacheSize));
1456         return result;
1457     }
1458
1459     if (WKStringIsEqualToUTF8CString(messageName, "AllowCacheStorageQuotaIncrease")) {
1460         TestController::singleton().allowCacheStorageQuotaIncrease();
1461         return nullptr;
1462     }
1463
1464     if (WKStringIsEqualToUTF8CString(messageName, "SetIDBPerOriginQuota")) {
1465         ASSERT(WKGetTypeID(messageBody) == WKUInt64GetTypeID());
1466         WKUInt64Ref quota = static_cast<WKUInt64Ref>(messageBody);
1467         TestController::singleton().setIDBPerOriginQuota(WKUInt64GetValue(quota));
1468         return nullptr;
1469     }
1470
1471     if (WKStringIsEqualToUTF8CString(messageName, "InjectUserScript")) {
1472         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
1473         WKStringRef script = static_cast<WKStringRef>(messageBody);
1474
1475         TestController::singleton().injectUserScript(script);
1476         return nullptr;
1477     }
1478
1479     if (WKStringIsEqualToUTF8CString(messageName, "GetApplicationManifest")) {
1480 #ifdef __BLOCKS__
1481         WKPageGetApplicationManifest_b(TestController::singleton().mainWebView()->page(), ^{
1482             WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("DidGetApplicationManifest"));
1483             WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
1484         });
1485 #else
1486         // FIXME: Add API for loading the manifest on non-__BLOCKS__ ports.
1487         ASSERT_NOT_REACHED();
1488 #endif
1489         return nullptr;
1490     }
1491
1492     if (WKStringIsEqualToUTF8CString(messageName, "SendDisplayConfigurationChangedMessageForTesting")) {
1493         TestController::singleton().sendDisplayConfigurationChangedMessageForTesting();
1494         return nullptr;
1495     }
1496
1497     if (WKStringIsEqualToUTF8CString(messageName, "TerminateNetworkProcess")) {
1498         ASSERT(!messageBody);
1499         TestController::singleton().terminateNetworkProcess();
1500         return nullptr;
1501     }
1502
1503     if (WKStringIsEqualToUTF8CString(messageName, "TerminateServiceWorkerProcess")) {
1504         ASSERT(!messageBody);
1505         TestController::singleton().terminateServiceWorkerProcess();
1506         return nullptr;
1507     }
1508
1509     if (WKStringIsEqualToUTF8CString(messageName, "SetWebAuthenticationMockConfiguration")) {
1510         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
1511         TestController::singleton().setWebAuthenticationMockConfiguration(static_cast<WKDictionaryRef>(messageBody));
1512         return nullptr;
1513     }
1514
1515     if (WKStringIsEqualToUTF8CString(messageName, "AddTestKeyToKeychain")) {
1516         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
1517         WKDictionaryRef testKeyDictionary = static_cast<WKDictionaryRef>(messageBody);
1518
1519         WKRetainPtr<WKStringRef> privateKeyKey(AdoptWK, WKStringCreateWithUTF8CString("PrivateKey"));
1520         WKStringRef privateKeyWK = static_cast<WKStringRef>(WKDictionaryGetItemForKey(testKeyDictionary, privateKeyKey.get()));
1521
1522         WKRetainPtr<WKStringRef> attrLabelKey(AdoptWK, WKStringCreateWithUTF8CString("AttrLabel"));
1523         WKStringRef attrLabelWK = static_cast<WKStringRef>(WKDictionaryGetItemForKey(testKeyDictionary, attrLabelKey.get()));
1524
1525         WKRetainPtr<WKStringRef> applicationTagKey(AdoptWK, WKStringCreateWithUTF8CString("ApplicationTag"));
1526         WKStringRef applicationTagWK = static_cast<WKStringRef>(WKDictionaryGetItemForKey(testKeyDictionary, applicationTagKey.get()));
1527
1528         TestController::singleton().addTestKeyToKeychain(toWTFString(privateKeyWK), toWTFString(attrLabelWK), toWTFString(applicationTagWK));
1529         return nullptr;
1530     }
1531
1532     if (WKStringIsEqualToUTF8CString(messageName, "CleanUpKeychain")) {
1533         ASSERT(WKGetTypeID(messageBody) == WKStringGetTypeID());
1534         TestController::singleton().cleanUpKeychain(toWTFString(static_cast<WKStringRef>(messageBody)));
1535         return nullptr;
1536     }
1537
1538     if (WKStringIsEqualToUTF8CString(messageName, "KeyExistsInKeychain")) {
1539         ASSERT(WKGetTypeID(messageBody) == WKDictionaryGetTypeID());
1540         WKDictionaryRef testDictionary = static_cast<WKDictionaryRef>(messageBody);
1541
1542         WKRetainPtr<WKStringRef> attrLabelKey(AdoptWK, WKStringCreateWithUTF8CString("AttrLabel"));
1543         WKStringRef attrLabelWK = static_cast<WKStringRef>(WKDictionaryGetItemForKey(testDictionary, attrLabelKey.get()));
1544
1545         WKRetainPtr<WKStringRef> applicationTagKey(AdoptWK, WKStringCreateWithUTF8CString("ApplicationTag"));
1546         WKStringRef applicationTagWK = static_cast<WKStringRef>(WKDictionaryGetItemForKey(testDictionary, applicationTagKey.get()));
1547
1548         bool keyExistsInKeychain = TestController::singleton().keyExistsInKeychain(toWTFString(attrLabelWK), toWTFString(applicationTagWK));
1549         WKRetainPtr<WKTypeRef> result(AdoptWK, WKBooleanCreate(keyExistsInKeychain));
1550         return result;
1551     }
1552
1553     if (WKStringIsEqualToUTF8CString(messageName, "SetCanHandleHTTPSServerTrustEvaluation")) {
1554         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
1555         auto canHandle = WKBooleanGetValue(static_cast<WKBooleanRef>(messageBody));
1556         WKContextSetCanHandleHTTPSServerTrustEvaluation(TestController::singleton().context(), canHandle);
1557         return nullptr;
1558     }
1559
1560     if (WKStringIsEqualToUTF8CString(messageName, "CanDoServerTrustEvaluationInNetworkProcess")) {
1561         WKRetainPtr<WKTypeRef> result(AdoptWK, WKBooleanCreate(TestController::singleton().canDoServerTrustEvaluationInNetworkProcess()));
1562         return result;
1563     }
1564
1565     if (WKStringIsEqualToUTF8CString(messageName, "ServerTrustEvaluationCallbackCallsCount")) {
1566         WKRetainPtr<WKTypeRef> result(AdoptWK, WKUInt64Create(TestController::singleton().serverTrustEvaluationCallbackCallsCount()));
1567         return result;
1568     }
1569
1570     if (WKStringIsEqualToUTF8CString(messageName, "ShouldDismissJavaScriptAlertsAsynchronously")) {
1571         ASSERT(WKGetTypeID(messageBody) == WKBooleanGetTypeID());
1572         WKBooleanRef value = static_cast<WKBooleanRef>(messageBody);
1573         TestController::singleton().setShouldDismissJavaScriptAlertsAsynchronously(WKBooleanGetValue(value));
1574         return nullptr;
1575     }
1576
1577     if (WKStringIsEqualToUTF8CString(messageName, "dumpAdClickAttribution")) {
1578         dumpAdClickAttribution();
1579         return nullptr;
1580     }
1581     
1582     if (WKStringIsEqualToUTF8CString(messageName, "clearAdClickAttribution")) {
1583         TestController::singleton().clearAdClickAttribution();
1584         return nullptr;
1585     }
1586     
1587     ASSERT_NOT_REACHED();
1588     return nullptr;
1589 }
1590
1591 void TestInvocation::runUISideScriptAfterUpdateCallback(WKErrorRef, void* context)
1592 {
1593     UIScriptInvocationData* data = static_cast<UIScriptInvocationData*>(context);
1594     if (TestInvocation* invocation = data->testInvocation) {
1595         RELEASE_ASSERT(TestController::singleton().isCurrentInvocation(invocation));
1596         invocation->runUISideScript(data->scriptString.get(), data->callbackID);
1597     }
1598     delete data;
1599 }
1600
1601 void TestInvocation::runUISideScript(WKStringRef script, unsigned scriptCallbackID)
1602 {
1603     m_pendingUIScriptInvocationData = nullptr;
1604
1605     if (!m_UIScriptContext)
1606         m_UIScriptContext = std::make_unique<UIScriptContext>(*this);
1607     
1608     m_UIScriptContext->runUIScript(toWTFString(script), scriptCallbackID);
1609 }
1610
1611 void TestInvocation::uiScriptDidComplete(const String& result, unsigned scriptCallbackID)
1612 {
1613     WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("CallUISideScriptCallback"));
1614
1615     WKRetainPtr<WKMutableDictionaryRef> messageBody(AdoptWK, WKMutableDictionaryCreate());
1616     WKRetainPtr<WKStringRef> resultKey(AdoptWK, WKStringCreateWithUTF8CString("Result"));
1617     WKRetainPtr<WKStringRef> callbackIDKey(AdoptWK, WKStringCreateWithUTF8CString("CallbackID"));
1618     WKRetainPtr<WKUInt64Ref> callbackIDValue = adoptWK(WKUInt64Create(scriptCallbackID));
1619
1620     WKDictionarySetItem(messageBody.get(), resultKey.get(), toWK(result).get());
1621     WKDictionarySetItem(messageBody.get(), callbackIDKey.get(), callbackIDValue.get());
1622
1623     WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), messageBody.get());
1624 }
1625
1626 void TestInvocation::outputText(const WTF::String& text)
1627 {
1628     m_textOutput.append(text);
1629 }
1630
1631 void TestInvocation::didBeginSwipe()
1632 {
1633     WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("CallDidBeginSwipeCallback"));
1634     WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
1635 }
1636
1637 void TestInvocation::willEndSwipe()
1638 {
1639     WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("CallWillEndSwipeCallback"));
1640     WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
1641 }
1642
1643 void TestInvocation::didEndSwipe()
1644 {
1645     WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("CallDidEndSwipeCallback"));
1646     WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
1647 }
1648
1649 void TestInvocation::didRemoveSwipeSnapshot()
1650 {
1651     WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("CallDidRemoveSwipeSnapshotCallback"));
1652     WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
1653 }
1654
1655 void TestInvocation::notifyDownloadDone()
1656 {
1657     WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("NotifyDownloadDone"));
1658     WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
1659 }
1660
1661 void TestInvocation::didClearStatisticsThroughWebsiteDataRemoval()
1662 {
1663     WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("CallDidClearStatisticsThroughWebsiteDataRemoval"));
1664     WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
1665 }
1666
1667 void TestInvocation::didResetStatisticsToConsistentState()
1668 {
1669     WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("CallDidResetStatisticsToConsistentState"));
1670     WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
1671 }
1672
1673 void TestInvocation::didSetBlockCookiesForHost()
1674 {
1675     WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("CallDidSetBlockCookiesForHost"));
1676     WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
1677 }
1678
1679 void TestInvocation::didSetStatisticsDebugMode()
1680 {
1681     WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("CallDidSetStatisticsDebugMode"));
1682     WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
1683 }
1684
1685 void TestInvocation::didSetPrevalentResourceForDebugMode()
1686 {
1687     WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("CallDidSetPrevalentResourceForDebugMode"));
1688     WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
1689 }
1690
1691 void TestInvocation::didSetLastSeen()
1692 {
1693     WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("CallDidSetLastSeen"));
1694     WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
1695 }
1696
1697 void TestInvocation::didSetPrevalentResource()
1698 {
1699     WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("CallDidSetPrevalentResource"));
1700     WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
1701 }
1702
1703 void TestInvocation::didSetVeryPrevalentResource()
1704 {
1705     WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("CallDidSetVeryPrevalentResource"));
1706     WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
1707 }
1708
1709 void TestInvocation::didSetHasHadUserInteraction()
1710 {
1711     WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("CallDidSetHasHadUserInteraction"));
1712     WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
1713 }
1714
1715 void TestInvocation::didReceiveAllStorageAccessEntries(Vector<String>& domains)
1716 {
1717     WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("CallDidReceiveAllStorageAccessEntries"));
1718     
1719     WKRetainPtr<WKMutableArrayRef> messageBody(AdoptWK, WKMutableArrayCreate());
1720     for (auto& domain : domains)
1721         WKArrayAppendItem(messageBody.get(), adoptWK(WKStringCreateWithUTF8CString(domain.utf8().data())).get());
1722     
1723     WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), messageBody.get());
1724 }
1725
1726 void TestInvocation::didRemoveAllSessionCredentials()
1727 {
1728     WKRetainPtr<WKStringRef> messageName = adoptWK(WKStringCreateWithUTF8CString("CallDidRemoveAllSessionCredentialsCallback"));
1729     WKPagePostMessageToInjectedBundle(TestController::singleton().mainWebView()->page(), messageName.get(), 0);
1730 }
1731
1732 void TestInvocation::dumpResourceLoadStatistics()
1733 {
1734     m_shouldDumpResourceLoadStatistics = true;
1735 }
1736
1737 void TestInvocation::dumpAdClickAttribution()
1738 {
1739     m_shouldDumpAdClickAttribution = true;
1740 }
1741
1742 } // namespace WTR