<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN"
"http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head><meta http-equiv="content-type" content="text/html; charset=utf-8" />
<title>[197172] trunk</title>
</head>
<body>

<style type="text/css"><!--
#msg dl.meta { border: 1px #006 solid; background: #369; padding: 6px; color: #fff; }
#msg dl.meta dt { float: left; width: 6em; font-weight: bold; }
#msg dt:after { content:':';}
#msg dl, #msg dt, #msg ul, #msg li, #header, #footer, #logmsg { font-family: verdana,arial,helvetica,sans-serif; font-size: 10pt;  }
#msg dl a { font-weight: bold}
#msg dl a:link    { color:#fc3; }
#msg dl a:active  { color:#ff0; }
#msg dl a:visited { color:#cc6; }
h3 { font-family: verdana,arial,helvetica,sans-serif; font-size: 10pt; font-weight: bold; }
#msg pre { overflow: auto; background: #ffc; border: 1px #fa0 solid; padding: 6px; }
#logmsg { background: #ffc; border: 1px #fa0 solid; padding: 1em 1em 0 1em; }
#logmsg p, #logmsg pre, #logmsg blockquote { margin: 0 0 1em 0; }
#logmsg p, #logmsg li, #logmsg dt, #logmsg dd { line-height: 14pt; }
#logmsg h1, #logmsg h2, #logmsg h3, #logmsg h4, #logmsg h5, #logmsg h6 { margin: .5em 0; }
#logmsg h1:first-child, #logmsg h2:first-child, #logmsg h3:first-child, #logmsg h4:first-child, #logmsg h5:first-child, #logmsg h6:first-child { margin-top: 0; }
#logmsg ul, #logmsg ol { padding: 0; list-style-position: inside; margin: 0 0 0 1em; }
#logmsg ul { text-indent: -1em; padding-left: 1em; }#logmsg ol { text-indent: -1.5em; padding-left: 1.5em; }
#logmsg > ul, #logmsg > ol { margin: 0 0 1em 0; }
#logmsg pre { background: #eee; padding: 1em; }
#logmsg blockquote { border: 1px solid #fa0; border-left-width: 10px; padding: 1em 1em 0 1em; background: white;}
#logmsg dl { margin: 0; }
#logmsg dt { font-weight: bold; }
#logmsg dd { margin: 0; padding: 0 0 0.5em 0; }
#logmsg dd:before { content:'\00bb';}
#logmsg table { border-spacing: 0px; border-collapse: collapse; border-top: 4px solid #fa0; border-bottom: 1px solid #fa0; background: #fff; }
#logmsg table th { text-align: left; font-weight: normal; padding: 0.2em 0.5em; border-top: 1px dotted #fa0; }
#logmsg table td { text-align: right; border-top: 1px dotted #fa0; padding: 0.2em 0.5em; }
#logmsg table thead th { text-align: center; border-bottom: 1px solid #fa0; }
#logmsg table th.Corner { text-align: left; }
#logmsg hr { border: none 0; border-top: 2px dashed #fa0; height: 1px; }
#header, #footer { color: #fff; background: #636; border: 1px #300 solid; padding: 6px; }
#patch { width: 100%; }
#patch h4 {font-family: verdana,arial,helvetica,sans-serif;font-size:10pt;padding:8px;background:#369;color:#fff;margin:0;}
#patch .propset h4, #patch .binary h4 {margin:0;}
#patch pre {padding:0;line-height:1.2em;margin:0;}
#patch .diff {width:100%;background:#eee;padding: 0 0 10px 0;overflow:auto;}
#patch .propset .diff, #patch .binary .diff  {padding:10px 0;}
#patch span {display:block;padding:0 10px;}
#patch .modfile, #patch .addfile, #patch .delfile, #patch .propset, #patch .binary, #patch .copfile {border:1px solid #ccc;margin:10px 0;}
#patch ins {background:#dfd;text-decoration:none;display:block;padding:0 10px;}
#patch del {background:#fdd;text-decoration:none;display:block;padding:0 10px;}
#patch .lines, .info {color:#888;background:#fff;}
--></style>
<div id="msg">
<dl class="meta">
<dt>Revision</dt> <dd><a href="http://trac.webkit.org/projects/webkit/changeset/197172">197172</a></dd>
<dt>Author</dt> <dd>weinig@apple.com</dd>
<dt>Date</dt> <dd>2016-02-26 09:50:50 -0800 (Fri, 26 Feb 2016)</dd>
</dl>

<h3>Log Message</h3>
<pre>Allow WKUserScripts to be run in isolated worlds
https://bugs.webkit.org/show_bug.cgi?id=154701

Reviewed by Anders Carlsson.

Source/WebKit2:

Adds support for using isolated worlds, called _WKUserContentWorlds in the SPI,
from the UIProcess.

* Shared/API/APIObject.h:
* Shared/Cocoa/APIObject.mm:
* UIProcess/API/APIUserContentWorld.cpp: Added.
(API::generateIdentifier):
(API::UserContentWorld::worldWithName):
(API::UserContentWorld::normalWorld):
(API::UserContentWorld::UserContentWorld):
(API::UserContentWorld::~UserContentWorld):
* UIProcess/API/APIUserContentWorld.h: Added.
Add new UserContentWorld type.

* UIProcess/API/APIUserScript.h:
Bind each user script to a particular _WKUserContentWorld.

* UIProcess/API/C/WKUserScriptRef.cpp:
(WKUserScriptCreateWithSource):
(WKUserScriptCopySource):
Existing APIs create user scripts for the normal world, preserving existing behavior.

* UIProcess/API/Cocoa/WKUserScript.mm:
(-[WKUserScript initWithSource:injectionTime:forMainFrameOnly:]):
Existing APIs create user scripts for the normal world, preserving existing behavior.

(-[WKUserScript _initWithSource:injectionTime:forMainFrameOnly:legacyWhitelist:legacyBlacklist:userContentWorld:]):
Add a new initializer which takes a world to bind to.  Also add support for the legacy whitelist/blacklist mechanism
while we are here, as the expected client needs these as well.

(-[WKUserScript _userContentWorld]):
Add accessor for the bound world.

* UIProcess/API/Cocoa/WKUserScriptInternal.h:
* UIProcess/API/Cocoa/WKUserScriptPrivate.h: Added.
Add new private header.

* UIProcess/API/Cocoa/_WKUserContentWorld.h: Added.
* UIProcess/API/Cocoa/_WKUserContentWorld.mm: Added.
(+[_WKUserContentWorld worldWithName:]):
(+[_WKUserContentWorld normalWorld]):
(-[_WKUserContentWorld dealloc]):
(-[_WKUserContentWorld name]):
(-[_WKUserContentWorld _apiObject]):
* UIProcess/API/Cocoa/_WKUserContentWorldInternal.h: Added.
Add SPI wrapper.

* UIProcess/UserContent/WebUserContentControllerProxy.cpp:
(WebKit::WebUserContentControllerProxy::addProcess):
(WebKit::WebUserContentControllerProxy::addUserScript):
(WebKit::WebUserContentControllerProxy::removeUserScript):
(WebKit::WebUserContentControllerProxy::removeAllUserScripts):
(WebKit::WebUserContentControllerProxy::addUserStyleSheet):
* UIProcess/UserContent/WebUserContentControllerProxy.h:
(WebKit::WebUserContentControllerProxy::userScripts):
(WebKit::WebUserContentControllerProxy::userStyleSheets):
Add support for registering the worlds with the associated WebContentProcesses and then using
their identifiers to map user scripts to the correct world.
        
* WebKit2.xcodeproj/project.pbxproj:
Add new files.

* WebProcess/InjectedBundle/API/Cocoa/WKWebProcessPlugInScriptWorld.h:
* WebProcess/InjectedBundle/API/Cocoa/WKWebProcessPlugInScriptWorld.mm:
(-[WKWebProcessPlugInScriptWorld name]):
Expose the name property.

* WebProcess/InjectedBundle/API/c/WKBundleScriptWorld.cpp:
(WKBundleScriptWorldCopyName):
* WebProcess/InjectedBundle/API/c/WKBundleScriptWorld.h:
Expose the name property.

* WebProcess/InjectedBundle/InjectedBundleScriptWorld.cpp:
(WebKit::allWorlds):
(WebKit::InjectedBundleScriptWorld::create):
(WebKit::InjectedBundleScriptWorld::getOrCreate):
(WebKit::InjectedBundleScriptWorld::normalWorld):
(WebKit::InjectedBundleScriptWorld::InjectedBundleScriptWorld):
(WebKit::InjectedBundleScriptWorld::~InjectedBundleScriptWorld):
(WebKit::InjectedBundleScriptWorld::coreWorld):
(WebKit::InjectedBundleScriptWorld::clearWrappers):
* WebProcess/InjectedBundle/InjectedBundleScriptWorld.h:
(WebKit::InjectedBundleScriptWorld::name):
Add the name property and do some drive-by RefPtr -&gt; Ref conversions.

* WebProcess/UserContent/WebUserContentController.cpp:
(WebKit::userContentControllers):
(WebKit::worldMap):
(WebKit::WebUserContentController::getOrCreate):
(WebKit::WebUserContentController::~WebUserContentController):
(WebKit::WebUserContentController::addUserContentWorlds):
(WebKit::WebUserContentController::removeUserContentWorld):
(WebKit::WebUserContentController::addUserScripts):
(WebKit::WebUserContentController::removeUserScript):
(WebKit::WebUserContentController::removeAllUserScripts):
(WebKit::WebUserContentController::addUserStyleSheets):
* WebProcess/UserContent/WebUserContentController.h:
* WebProcess/UserContent/WebUserContentController.messages.in:
Track and use worlds passed from the UIProcess.

Tools:

* TestWebKitAPI/TestWebKitAPI.xcodeproj/project.pbxproj:
* TestWebKitAPI/Tests/WebKit2Cocoa/_WKUserContentWorld.mm: Added.
(-[SimpleDelegate webView:didFinishNavigation:]):
(-[UserContentWorldRemoteObject didObserveNormalWorld]):
(-[UserContentWorldRemoteObject didObserveWorldWithName:]):
* TestWebKitAPI/Tests/WebKit2Cocoa/_WKUserContentWorldPlugIn.mm: Added.
(-[_WKUserContentWorldPlugIn webProcessPlugIn:didCreateBrowserContextController:]):
(-[_WKUserContentWorldPlugIn webProcessPlugInBrowserContextController:globalObjectIsAvailableForFrame:inScriptWorld:]):
* TestWebKitAPI/Tests/WebKit2Cocoa/_WKUserContentWorldProtocol.h: Added.</pre>

<h3>Modified Paths</h3>
<ul>
<li><a href="#trunkSourceWebKit2ChangeLog">trunk/Source/WebKit2/ChangeLog</a></li>
<li><a href="#trunkSourceWebKit2SharedAPIAPIObjecth">trunk/Source/WebKit2/Shared/API/APIObject.h</a></li>
<li><a href="#trunkSourceWebKit2SharedCocoaAPIObjectmm">trunk/Source/WebKit2/Shared/Cocoa/APIObject.mm</a></li>
<li><a href="#trunkSourceWebKit2UIProcessAPIAPIUserScripth">trunk/Source/WebKit2/UIProcess/API/APIUserScript.h</a></li>
<li><a href="#trunkSourceWebKit2UIProcessAPICWKUserScriptRefcpp">trunk/Source/WebKit2/UIProcess/API/C/WKUserScriptRef.cpp</a></li>
<li><a href="#trunkSourceWebKit2UIProcessAPICocoaWKUserScriptmm">trunk/Source/WebKit2/UIProcess/API/Cocoa/WKUserScript.mm</a></li>
<li><a href="#trunkSourceWebKit2UIProcessAPICocoaWKUserScriptInternalh">trunk/Source/WebKit2/UIProcess/API/Cocoa/WKUserScriptInternal.h</a></li>
<li><a href="#trunkSourceWebKit2UIProcessUserContentWebUserContentControllerProxycpp">trunk/Source/WebKit2/UIProcess/UserContent/WebUserContentControllerProxy.cpp</a></li>
<li><a href="#trunkSourceWebKit2UIProcessUserContentWebUserContentControllerProxyh">trunk/Source/WebKit2/UIProcess/UserContent/WebUserContentControllerProxy.h</a></li>
<li><a href="#trunkSourceWebKit2WebKit2xcodeprojprojectpbxproj">trunk/Source/WebKit2/WebKit2.xcodeproj/project.pbxproj</a></li>
<li><a href="#trunkSourceWebKit2WebProcessInjectedBundleAPICocoaWKWebProcessPlugInScriptWorldh">trunk/Source/WebKit2/WebProcess/InjectedBundle/API/Cocoa/WKWebProcessPlugInScriptWorld.h</a></li>
<li><a href="#trunkSourceWebKit2WebProcessInjectedBundleAPICocoaWKWebProcessPlugInScriptWorldmm">trunk/Source/WebKit2/WebProcess/InjectedBundle/API/Cocoa/WKWebProcessPlugInScriptWorld.mm</a></li>
<li><a href="#trunkSourceWebKit2WebProcessInjectedBundleAPIcWKBundleScriptWorldcpp">trunk/Source/WebKit2/WebProcess/InjectedBundle/API/c/WKBundleScriptWorld.cpp</a></li>
<li><a href="#trunkSourceWebKit2WebProcessInjectedBundleAPIcWKBundleScriptWorldh">trunk/Source/WebKit2/WebProcess/InjectedBundle/API/c/WKBundleScriptWorld.h</a></li>
<li><a href="#trunkSourceWebKit2WebProcessInjectedBundleInjectedBundleScriptWorldcpp">trunk/Source/WebKit2/WebProcess/InjectedBundle/InjectedBundleScriptWorld.cpp</a></li>
<li><a href="#trunkSourceWebKit2WebProcessInjectedBundleInjectedBundleScriptWorldh">trunk/Source/WebKit2/WebProcess/InjectedBundle/InjectedBundleScriptWorld.h</a></li>
<li><a href="#trunkSourceWebKit2WebProcessUserContentWebUserContentControllercpp">trunk/Source/WebKit2/WebProcess/UserContent/WebUserContentController.cpp</a></li>
<li><a href="#trunkSourceWebKit2WebProcessUserContentWebUserContentControllerh">trunk/Source/WebKit2/WebProcess/UserContent/WebUserContentController.h</a></li>
<li><a href="#trunkSourceWebKit2WebProcessUserContentWebUserContentControllermessagesin">trunk/Source/WebKit2/WebProcess/UserContent/WebUserContentController.messages.in</a></li>
<li><a href="#trunkToolsChangeLog">trunk/Tools/ChangeLog</a></li>
<li><a href="#trunkToolsTestWebKitAPITestWebKitAPIxcodeprojprojectpbxproj">trunk/Tools/TestWebKitAPI/TestWebKitAPI.xcodeproj/project.pbxproj</a></li>
</ul>

<h3>Added Paths</h3>
<ul>
<li><a href="#trunkSourceWebKit2UIProcessAPIAPIUserContentWorldcpp">trunk/Source/WebKit2/UIProcess/API/APIUserContentWorld.cpp</a></li>
<li><a href="#trunkSourceWebKit2UIProcessAPIAPIUserContentWorldh">trunk/Source/WebKit2/UIProcess/API/APIUserContentWorld.h</a></li>
<li><a href="#trunkSourceWebKit2UIProcessAPICocoaWKUserScriptPrivateh">trunk/Source/WebKit2/UIProcess/API/Cocoa/WKUserScriptPrivate.h</a></li>
<li><a href="#trunkSourceWebKit2UIProcessAPICocoa_WKUserContentWorldh">trunk/Source/WebKit2/UIProcess/API/Cocoa/_WKUserContentWorld.h</a></li>
<li><a href="#trunkSourceWebKit2UIProcessAPICocoa_WKUserContentWorldmm">trunk/Source/WebKit2/UIProcess/API/Cocoa/_WKUserContentWorld.mm</a></li>
<li><a href="#trunkSourceWebKit2UIProcessAPICocoa_WKUserContentWorldInternalh">trunk/Source/WebKit2/UIProcess/API/Cocoa/_WKUserContentWorldInternal.h</a></li>
<li><a href="#trunkToolsTestWebKitAPITestsWebKit2CocoaUserContentWorldmm">trunk/Tools/TestWebKitAPI/Tests/WebKit2Cocoa/UserContentWorld.mm</a></li>
<li><a href="#trunkToolsTestWebKitAPITestsWebKit2CocoaUserContentWorldPlugInmm">trunk/Tools/TestWebKitAPI/Tests/WebKit2Cocoa/UserContentWorldPlugIn.mm</a></li>
<li><a href="#trunkToolsTestWebKitAPITestsWebKit2CocoaUserContentWorldProtocolh">trunk/Tools/TestWebKitAPI/Tests/WebKit2Cocoa/UserContentWorldProtocol.h</a></li>
</ul>

</div>
<div id="patch">
<h3>Diff</h3>
<a id="trunkSourceWebKit2ChangeLog"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit2/ChangeLog (197171 => 197172)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/ChangeLog        2016-02-26 17:36:41 UTC (rev 197171)
+++ trunk/Source/WebKit2/ChangeLog        2016-02-26 17:50:50 UTC (rev 197172)
</span><span class="lines">@@ -1,3 +1,110 @@
</span><ins>+2016-02-25  Sam Weinig  &lt;sam@webkit.org&gt;
+
+        Allow WKUserScripts to be run in isolated worlds
+        https://bugs.webkit.org/show_bug.cgi?id=154701
+
+        Reviewed by Anders Carlsson.
+
+        Adds support for using isolated worlds, called _WKUserContentWorlds in the SPI,
+        from the UIProcess.
+
+        * Shared/API/APIObject.h:
+        * Shared/Cocoa/APIObject.mm:
+        * UIProcess/API/APIUserContentWorld.cpp: Added.
+        (API::generateIdentifier):
+        (API::UserContentWorld::worldWithName):
+        (API::UserContentWorld::normalWorld):
+        (API::UserContentWorld::UserContentWorld):
+        (API::UserContentWorld::~UserContentWorld):
+        * UIProcess/API/APIUserContentWorld.h: Added.
+        Add new UserContentWorld type.
+
+        * UIProcess/API/APIUserScript.h:
+        Bind each user script to a particular _WKUserContentWorld.
+
+        * UIProcess/API/C/WKUserScriptRef.cpp:
+        (WKUserScriptCreateWithSource):
+        (WKUserScriptCopySource):
+        Existing APIs create user scripts for the normal world, preserving existing behavior.
+
+        * UIProcess/API/Cocoa/WKUserScript.mm:
+        (-[WKUserScript initWithSource:injectionTime:forMainFrameOnly:]):
+        Existing APIs create user scripts for the normal world, preserving existing behavior.
+
+        (-[WKUserScript _initWithSource:injectionTime:forMainFrameOnly:legacyWhitelist:legacyBlacklist:userContentWorld:]):
+        Add a new initializer which takes a world to bind to.  Also add support for the legacy whitelist/blacklist mechanism
+        while we are here, as the expected client needs these as well.
+
+        (-[WKUserScript _userContentWorld]):
+        Add accessor for the bound world.
+
+        * UIProcess/API/Cocoa/WKUserScriptInternal.h:
+        * UIProcess/API/Cocoa/WKUserScriptPrivate.h: Added.
+        Add new private header.
+
+        * UIProcess/API/Cocoa/_WKUserContentWorld.h: Added.
+        * UIProcess/API/Cocoa/_WKUserContentWorld.mm: Added.
+        (+[_WKUserContentWorld worldWithName:]):
+        (+[_WKUserContentWorld normalWorld]):
+        (-[_WKUserContentWorld dealloc]):
+        (-[_WKUserContentWorld name]):
+        (-[_WKUserContentWorld _apiObject]):
+        * UIProcess/API/Cocoa/_WKUserContentWorldInternal.h: Added.
+        Add SPI wrapper.
+
+        * UIProcess/UserContent/WebUserContentControllerProxy.cpp:
+        (WebKit::WebUserContentControllerProxy::addProcess):
+        (WebKit::WebUserContentControllerProxy::addUserScript):
+        (WebKit::WebUserContentControllerProxy::removeUserScript):
+        (WebKit::WebUserContentControllerProxy::removeAllUserScripts):
+        (WebKit::WebUserContentControllerProxy::addUserStyleSheet):
+        * UIProcess/UserContent/WebUserContentControllerProxy.h:
+        (WebKit::WebUserContentControllerProxy::userScripts):
+        (WebKit::WebUserContentControllerProxy::userStyleSheets):
+        Add support for registering the worlds with the associated WebContentProcesses and then using
+        their identifiers to map user scripts to the correct world.
+        
+        * WebKit2.xcodeproj/project.pbxproj:
+        Add new files.
+
+        * WebProcess/InjectedBundle/API/Cocoa/WKWebProcessPlugInScriptWorld.h:
+        * WebProcess/InjectedBundle/API/Cocoa/WKWebProcessPlugInScriptWorld.mm:
+        (-[WKWebProcessPlugInScriptWorld name]):
+        Expose the name property.
+
+        * WebProcess/InjectedBundle/API/c/WKBundleScriptWorld.cpp:
+        (WKBundleScriptWorldCopyName):
+        * WebProcess/InjectedBundle/API/c/WKBundleScriptWorld.h:
+        Expose the name property.
+
+        * WebProcess/InjectedBundle/InjectedBundleScriptWorld.cpp:
+        (WebKit::allWorlds):
+        (WebKit::InjectedBundleScriptWorld::create):
+        (WebKit::InjectedBundleScriptWorld::getOrCreate):
+        (WebKit::InjectedBundleScriptWorld::normalWorld):
+        (WebKit::InjectedBundleScriptWorld::InjectedBundleScriptWorld):
+        (WebKit::InjectedBundleScriptWorld::~InjectedBundleScriptWorld):
+        (WebKit::InjectedBundleScriptWorld::coreWorld):
+        (WebKit::InjectedBundleScriptWorld::clearWrappers):
+        * WebProcess/InjectedBundle/InjectedBundleScriptWorld.h:
+        (WebKit::InjectedBundleScriptWorld::name):
+        Add the name property and do some drive-by RefPtr -&gt; Ref conversions.
+
+        * WebProcess/UserContent/WebUserContentController.cpp:
+        (WebKit::userContentControllers):
+        (WebKit::worldMap):
+        (WebKit::WebUserContentController::getOrCreate):
+        (WebKit::WebUserContentController::~WebUserContentController):
+        (WebKit::WebUserContentController::addUserContentWorlds):
+        (WebKit::WebUserContentController::removeUserContentWorld):
+        (WebKit::WebUserContentController::addUserScripts):
+        (WebKit::WebUserContentController::removeUserScript):
+        (WebKit::WebUserContentController::removeAllUserScripts):
+        (WebKit::WebUserContentController::addUserStyleSheets):
+        * WebProcess/UserContent/WebUserContentController.h:
+        * WebProcess/UserContent/WebUserContentController.messages.in:
+        Track and use worlds passed from the UIProcess.
+
</ins><span class="cx"> 2016-02-26  Andreas Kling  &lt;akling@apple.com&gt;
</span><span class="cx"> 
</span><span class="cx">         [Darwin] Use vm_kernel_page_size for WTF::pageSize().
</span></span></pre></div>
<a id="trunkSourceWebKit2SharedAPIAPIObjecth"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit2/Shared/API/APIObject.h (197171 => 197172)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/Shared/API/APIObject.h        2016-02-26 17:36:41 UTC (rev 197171)
+++ trunk/Source/WebKit2/Shared/API/APIObject.h        2016-02-26 17:50:50 UTC (rev 197172)
</span><span class="lines">@@ -147,6 +147,7 @@
</span><span class="cx">         UserContentController,
</span><span class="cx">         UserContentExtension,
</span><span class="cx">         UserContentExtensionStore,
</span><ins>+        UserContentWorld,
</ins><span class="cx">         UserMediaPermissionCheck,
</span><span class="cx">         UserMediaPermissionRequest,
</span><span class="cx">         Vibration,
</span></span></pre></div>
<a id="trunkSourceWebKit2SharedCocoaAPIObjectmm"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit2/Shared/Cocoa/APIObject.mm (197171 => 197172)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/Shared/Cocoa/APIObject.mm        2016-02-26 17:36:41 UTC (rev 197171)
+++ trunk/Source/WebKit2/Shared/Cocoa/APIObject.mm        2016-02-26 17:50:50 UTC (rev 197172)
</span><span class="lines">@@ -68,6 +68,7 @@
</span><span class="cx"> #import &quot;_WKProcessPoolConfigurationInternal.h&quot;
</span><span class="cx"> #import &quot;_WKUserContentExtensionStoreInternal.h&quot;
</span><span class="cx"> #import &quot;_WKUserContentFilterInternal.h&quot;
</span><ins>+#import &quot;_WKUserContentWorldInternal.h&quot;
</ins><span class="cx"> #import &quot;_WKUserStyleSheetInternal.h&quot;
</span><span class="cx"> #import &quot;_WKVisitedLinkStoreInternal.h&quot;
</span><span class="cx"> 
</span><span class="lines">@@ -212,6 +213,10 @@
</span><span class="cx">         wrapper = [_WKUserContentExtensionStore alloc];
</span><span class="cx">         break;
</span><span class="cx"> 
</span><ins>+    case Type::UserContentWorld:
+        wrapper = [_WKUserContentWorld alloc];
+        break;
+
</ins><span class="cx">     case Type::UserScript:
</span><span class="cx">         wrapper = [WKUserScript alloc];
</span><span class="cx">         break;
</span></span></pre></div>
<a id="trunkSourceWebKit2UIProcessAPIAPIUserContentWorldcpp"></a>
<div class="addfile"><h4>Added: trunk/Source/WebKit2/UIProcess/API/APIUserContentWorld.cpp (0 => 197172)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/UIProcess/API/APIUserContentWorld.cpp                                (rev 0)
+++ trunk/Source/WebKit2/UIProcess/API/APIUserContentWorld.cpp        2016-02-26 17:50:50 UTC (rev 197172)
</span><span class="lines">@@ -0,0 +1,68 @@
</span><ins>+/*
+ * Copyright (C) 2016 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include &quot;config.h&quot;
+#include &quot;APIUserContentWorld.h&quot;
+
+#include &lt;wtf/NeverDestroyed.h&gt;
+
+namespace API {
+
+static const uint64_t normalWorldIdentifer = 1;
+
+static uint64_t generateIdentifier()
+{
+    static uint64_t identifier = normalWorldIdentifer;
+
+    return ++identifier;
+}
+
+Ref&lt;UserContentWorld&gt; UserContentWorld::worldWithName(const WTF::String&amp; name)
+{
+    return adoptRef(*new UserContentWorld(name));
+}
+
+UserContentWorld&amp; UserContentWorld::normalWorld()
+{
+    static UserContentWorld* world = new UserContentWorld(ForNormalWorldOnly::NormalWorld);
+    return *world;
+}
+
+UserContentWorld::UserContentWorld(const WTF::String&amp; name)
+    : m_identifier(generateIdentifier())
+    , m_name(name)
+{
+}
+
+UserContentWorld::UserContentWorld(ForNormalWorldOnly)
+    : m_identifier(normalWorldIdentifer)
+{
+}
+
+UserContentWorld::~UserContentWorld()
+{
+}
+
+} // namespace API
</ins></span></pre></div>
<a id="trunkSourceWebKit2UIProcessAPIAPIUserContentWorldh"></a>
<div class="addfile"><h4>Added: trunk/Source/WebKit2/UIProcess/API/APIUserContentWorld.h (0 => 197172)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/UIProcess/API/APIUserContentWorld.h                                (rev 0)
+++ trunk/Source/WebKit2/UIProcess/API/APIUserContentWorld.h        2016-02-26 17:50:50 UTC (rev 197172)
</span><span class="lines">@@ -0,0 +1,56 @@
</span><ins>+/*
+ * Copyright (C) 2016 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef APIUserContentWorld_h
+#define APIUserContentWorld_h
+
+#include &quot;APIObject.h&quot;
+#include &lt;wtf/text/WTFString.h&gt;
+
+namespace API {
+
+class UserContentWorld final : public API::ObjectImpl&lt;API::Object::Type::UserContentWorld&gt; {
+public:
+    static Ref&lt;UserContentWorld&gt; worldWithName(const WTF::String&amp;);
+    static UserContentWorld&amp; normalWorld();
+
+    virtual ~UserContentWorld();
+
+    const WTF::String&amp; name() const { return m_name; }
+    uint64_t identifier() const { return m_identifier; }
+
+private:
+    UserContentWorld(const WTF::String&amp;);
+
+    enum class ForNormalWorldOnly { NormalWorld };
+    UserContentWorld(ForNormalWorldOnly);
+
+    uint64_t m_identifier;
+    WTF::String m_name;
+};
+
+} // namespace API
+
+#endif // APIUserContentWorld_h
</ins></span></pre></div>
<a id="trunkSourceWebKit2UIProcessAPIAPIUserScripth"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit2/UIProcess/API/APIUserScript.h (197171 => 197172)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/UIProcess/API/APIUserScript.h        2016-02-26 17:36:41 UTC (rev 197171)
+++ trunk/Source/WebKit2/UIProcess/API/APIUserScript.h        2016-02-26 17:50:50 UTC (rev 197172)
</span><span class="lines">@@ -27,6 +27,7 @@
</span><span class="cx"> #define APIUserScript_h
</span><span class="cx"> 
</span><span class="cx"> #include &quot;APIObject.h&quot;
</span><ins>+#include &quot;APIUserContentWorld.h&quot;
</ins><span class="cx"> #include &lt;WebCore/UserScript.h&gt;
</span><span class="cx"> 
</span><span class="cx"> namespace API {
</span><span class="lines">@@ -35,20 +36,25 @@
</span><span class="cx"> public:
</span><span class="cx">     static WebCore::URL generateUniqueURL();
</span><span class="cx"> 
</span><del>-    static Ref&lt;UserScript&gt; create(WebCore::UserScript userScript)
</del><ins>+    static Ref&lt;UserScript&gt; create(WebCore::UserScript userScript, API::UserContentWorld&amp; world)
</ins><span class="cx">     {
</span><del>-        return adoptRef(*new UserScript(WTFMove(userScript)));
</del><ins>+        return adoptRef(*new UserScript(WTFMove(userScript), world));
</ins><span class="cx">     }
</span><span class="cx"> 
</span><del>-    UserScript(WebCore::UserScript userScript)
</del><ins>+    UserScript(WebCore::UserScript userScript, API::UserContentWorld&amp; world)
</ins><span class="cx">         : m_userScript(userScript)
</span><ins>+        , m_world(world)
</ins><span class="cx">     {
</span><span class="cx">     }
</span><span class="cx"> 
</span><span class="cx">     const WebCore::UserScript&amp; userScript() const { return m_userScript; }
</span><del>-
</del><ins>+    
+    UserContentWorld&amp; userContentWorld() { return m_world; }
+    const UserContentWorld&amp; userContentWorld() const { return m_world; }
+    
</ins><span class="cx"> private:
</span><span class="cx">     WebCore::UserScript m_userScript;
</span><ins>+    Ref&lt;UserContentWorld&gt; m_world;
</ins><span class="cx"> };
</span><span class="cx"> 
</span><span class="cx"> } // namespace API
</span></span></pre></div>
<a id="trunkSourceWebKit2UIProcessAPICWKUserScriptRefcpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit2/UIProcess/API/C/WKUserScriptRef.cpp (197171 => 197172)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/UIProcess/API/C/WKUserScriptRef.cpp        2016-02-26 17:36:41 UTC (rev 197171)
+++ trunk/Source/WebKit2/UIProcess/API/C/WKUserScriptRef.cpp        2016-02-26 17:50:50 UTC (rev 197172)
</span><span class="lines">@@ -38,7 +38,7 @@
</span><span class="cx"> 
</span><span class="cx"> WKUserScriptRef WKUserScriptCreateWithSource(WKStringRef sourceRef, _WKUserScriptInjectionTime injectionTime, bool forMainFrameOnly)
</span><span class="cx"> {
</span><del>-    return toAPI(&amp;API::UserScript::create(WebCore::UserScript { toWTFString(sourceRef), API::UserScript::generateUniqueURL(), { }, { }, toUserScriptInjectionTime(injectionTime), forMainFrameOnly ? WebCore::InjectInTopFrameOnly : WebCore::InjectInAllFrames }).leakRef());
</del><ins>+    return toAPI(&amp;API::UserScript::create(WebCore::UserScript { toWTFString(sourceRef), API::UserScript::generateUniqueURL(), { }, { }, toUserScriptInjectionTime(injectionTime), forMainFrameOnly ? WebCore::InjectInTopFrameOnly : WebCore::InjectInAllFrames }, API::UserContentWorld::normalWorld()).leakRef());
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> WKStringRef WKUserScriptCopySource(WKUserScriptRef userScriptRef)
</span></span></pre></div>
<a id="trunkSourceWebKit2UIProcessAPICocoaWKUserScriptmm"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit2/UIProcess/API/Cocoa/WKUserScript.mm (197171 => 197172)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/UIProcess/API/Cocoa/WKUserScript.mm        2016-02-26 17:36:41 UTC (rev 197171)
+++ trunk/Source/WebKit2/UIProcess/API/Cocoa/WKUserScript.mm        2016-02-26 17:50:50 UTC (rev 197172)
</span><span class="lines">@@ -26,6 +26,8 @@
</span><span class="cx"> #import &quot;config.h&quot;
</span><span class="cx"> #import &quot;WKUserScriptInternal.h&quot;
</span><span class="cx"> 
</span><ins>+#import &quot;_WKUserContentWorldInternal.h&quot;
+
</ins><span class="cx"> #if WK_API_ENABLED
</span><span class="cx"> 
</span><span class="cx"> @implementation WKUserScript
</span><span class="lines">@@ -35,7 +37,7 @@
</span><span class="cx">     if (!(self = [super init]))
</span><span class="cx">         return nil;
</span><span class="cx"> 
</span><del>-    API::Object::constructInWrapper&lt;API::UserScript&gt;(self, WebCore::UserScript { WTF::String(source), API::UserScript::generateUniqueURL(), { }, { }, API::toWebCoreUserScriptInjectionTime(injectionTime), forMainFrameOnly ? WebCore::InjectInTopFrameOnly : WebCore::InjectInAllFrames });
</del><ins>+    API::Object::constructInWrapper&lt;API::UserScript&gt;(self, WebCore::UserScript { WTF::String(source), API::UserScript::generateUniqueURL(), { }, { }, API::toWebCoreUserScriptInjectionTime(injectionTime), forMainFrameOnly ? WebCore::InjectInTopFrameOnly : WebCore::InjectInAllFrames }, API::UserContentWorld::normalWorld());
</ins><span class="cx"> 
</span><span class="cx">     return self;
</span><span class="cx"> }
</span><span class="lines">@@ -69,4 +71,37 @@
</span><span class="cx"> 
</span><span class="cx"> @end
</span><span class="cx"> 
</span><ins>+@implementation WKUserScript (WKPrivate)
+
+static Vector&lt;WTF::String&gt; toStringVector(NSArray&lt;NSString *&gt; *input)
+{
+    Vector&lt;WTF::String&gt; vector;
+
+    NSUInteger size = input.count;
+    if (!size)
+        return vector;
+
+    vector.reserveInitialCapacity(size);
+    for (NSString *string : input)
+        vector.uncheckedAppend(string);
+    return vector;
+}
+
+- (instancetype)_initWithSource:(NSString *)source injectionTime:(WKUserScriptInjectionTime)injectionTime forMainFrameOnly:(BOOL)forMainFrameOnly legacyWhitelist:(NSArray&lt;NSString *&gt; *)legacyWhitelist legacyBlacklist:(NSArray&lt;NSString *&gt; *)legacyBlacklist userContentWorld:(_WKUserContentWorld *)userContentWorld
+{
+    if (!(self = [super init]))
+        return nil;
+
+    API::Object::constructInWrapper&lt;API::UserScript&gt;(self, WebCore::UserScript { WTF::String(source), API::UserScript::generateUniqueURL(), toStringVector(legacyWhitelist), toStringVector(legacyBlacklist), API::toWebCoreUserScriptInjectionTime(injectionTime), forMainFrameOnly ? WebCore::InjectInTopFrameOnly : WebCore::InjectInAllFrames }, *userContentWorld-&gt;_userContentWorld);
+
+    return self;
+}
+
+- (_WKUserContentWorld *)_userContentWorld
+{
+    return API::wrapper(_userScript-&gt;userContentWorld());
+}
+
+@end
+
</ins><span class="cx"> #endif
</span></span></pre></div>
<a id="trunkSourceWebKit2UIProcessAPICocoaWKUserScriptInternalh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit2/UIProcess/API/Cocoa/WKUserScriptInternal.h (197171 => 197172)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/UIProcess/API/Cocoa/WKUserScriptInternal.h        2016-02-26 17:36:41 UTC (rev 197171)
+++ trunk/Source/WebKit2/UIProcess/API/Cocoa/WKUserScriptInternal.h        2016-02-26 17:50:50 UTC (rev 197172)
</span><span class="lines">@@ -23,7 +23,7 @@
</span><span class="cx">  * THE POSSIBILITY OF SUCH DAMAGE.
</span><span class="cx">  */
</span><span class="cx"> 
</span><del>-#import &quot;WKUserScript.h&quot;
</del><ins>+#import &quot;WKUserScriptPrivate.h&quot;
</ins><span class="cx"> 
</span><span class="cx"> #if WK_API_ENABLED
</span><span class="cx"> 
</span></span></pre></div>
<a id="trunkSourceWebKit2UIProcessAPICocoaWKUserScriptPrivateh"></a>
<div class="addfile"><h4>Added: trunk/Source/WebKit2/UIProcess/API/Cocoa/WKUserScriptPrivate.h (0 => 197172)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/UIProcess/API/Cocoa/WKUserScriptPrivate.h                                (rev 0)
+++ trunk/Source/WebKit2/UIProcess/API/Cocoa/WKUserScriptPrivate.h        2016-02-26 17:50:50 UTC (rev 197172)
</span><span class="lines">@@ -0,0 +1,44 @@
</span><ins>+/*
+ * Copyright (C) 2016 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import &lt;WebKit/WKUserScript.h&gt;
+
+#if WK_API_ENABLED
+
+NS_ASSUME_NONNULL_BEGIN
+
+@class _WKUserContentWorld;
+
+@interface WKUserScript (WKPrivate)
+
+- (instancetype)_initWithSource:(NSString *)source injectionTime:(WKUserScriptInjectionTime)injectionTime forMainFrameOnly:(BOOL)forMainFrameOnly legacyWhitelist:(NSArray&lt;NSString *&gt; *)legacyWhitelist legacyBlacklist:(NSArray&lt;NSString *&gt; *)legacyBlacklist userContentWorld:(_WKUserContentWorld *)userContentWorld WK_AVAILABLE(WK_MAC_TBA, WK_IOS_TBA);
+
+@property (nonatomic, readonly) _WKUserContentWorld *_userContentWorld WK_AVAILABLE(WK_MAC_TBA, WK_IOS_TBA);
+
+@end
+
+NS_ASSUME_NONNULL_END
+
+#endif
</ins></span></pre></div>
<a id="trunkSourceWebKit2UIProcessAPICocoa_WKUserContentWorldh"></a>
<div class="addfile"><h4>Added: trunk/Source/WebKit2/UIProcess/API/Cocoa/_WKUserContentWorld.h (0 => 197172)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/UIProcess/API/Cocoa/_WKUserContentWorld.h                                (rev 0)
+++ trunk/Source/WebKit2/UIProcess/API/Cocoa/_WKUserContentWorld.h        2016-02-26 17:50:50 UTC (rev 197172)
</span><span class="lines">@@ -0,0 +1,44 @@
</span><ins>+/*
+ * Copyright (C) 2016 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import &lt;WebKit/WKFoundation.h&gt;
+
+#if WK_API_ENABLED
+
+NS_ASSUME_NONNULL_BEGIN
+
+WK_CLASS_AVAILABLE(WK_MAC_TBA, WK_IOS_TBA)
+@interface _WKUserContentWorld : NSObject
+
++ (_WKUserContentWorld *)worldWithName:(NSString *)name;
++ (_WKUserContentWorld *)normalWorld;
+
+@property (nullable, nonatomic, readonly, copy) NSString *name;
+
+@end
+
+NS_ASSUME_NONNULL_END
+
+#endif // WK_API_ENABLED
</ins></span></pre></div>
<a id="trunkSourceWebKit2UIProcessAPICocoa_WKUserContentWorldmm"></a>
<div class="addfile"><h4>Added: trunk/Source/WebKit2/UIProcess/API/Cocoa/_WKUserContentWorld.mm (0 => 197172)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/UIProcess/API/Cocoa/_WKUserContentWorld.mm                                (rev 0)
+++ trunk/Source/WebKit2/UIProcess/API/Cocoa/_WKUserContentWorld.mm        2016-02-26 17:50:50 UTC (rev 197172)
</span><span class="lines">@@ -0,0 +1,66 @@
</span><ins>+/*
+ * Copyright (C) 2016 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import &quot;config.h&quot;
+#import &quot;_WKUserContentWorldInternal.h&quot;
+
+#if WK_API_ENABLED
+
+@implementation _WKUserContentWorld
+
++ (_WKUserContentWorld *)worldWithName:(NSString *)name
+{
+    return [wrapper(API::UserContentWorld::worldWithName(name).leakRef()) autorelease];
+}
+
++ (_WKUserContentWorld *)normalWorld
+{
+    return wrapper(API::UserContentWorld::normalWorld());
+}
+
+- (void)dealloc
+{
+    _userContentWorld-&gt;~UserContentWorld();
+
+    [super dealloc];
+}
+
+- (NSString *)name
+{
+    if (_userContentWorld.get() == &amp;API::UserContentWorld::normalWorld())
+        return nil;
+    return _userContentWorld-&gt;name();
+}
+
+#pragma mark WKObject protocol implementation
+
+- (API::Object&amp;)_apiObject
+{
+    return *_userContentWorld;
+}
+
+@end
+
+#endif
</ins></span></pre></div>
<a id="trunkSourceWebKit2UIProcessAPICocoa_WKUserContentWorldInternalh"></a>
<div class="addfile"><h4>Added: trunk/Source/WebKit2/UIProcess/API/Cocoa/_WKUserContentWorldInternal.h (0 => 197172)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/UIProcess/API/Cocoa/_WKUserContentWorldInternal.h                                (rev 0)
+++ trunk/Source/WebKit2/UIProcess/API/Cocoa/_WKUserContentWorldInternal.h        2016-02-26 17:50:50 UTC (rev 197172)
</span><span class="lines">@@ -0,0 +1,49 @@
</span><ins>+/*
+ * Copyright (C) 2016 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import &quot;_WKUserContentWorld.h&quot;
+
+#if WK_API_ENABLED
+
+#import &quot;APIUserContentWorld.h&quot;
+#import &quot;WKObject.h&quot;
+
+namespace API {
+
+inline _WKUserContentWorld *wrapper(UserContentWorld&amp; userContentWorld)
+{
+    ASSERT([userContentWorld.wrapper() isKindOfClass:[_WKUserContentWorld class]]);
+    return (_WKUserContentWorld *)userContentWorld.wrapper();
+}
+
+}
+
+@interface _WKUserContentWorld () &lt;WKObject&gt; {
+@package
+    API::ObjectStorage&lt;API::UserContentWorld&gt; _userContentWorld;
+}
+@end
+
+#endif
</ins></span></pre></div>
<a id="trunkSourceWebKit2UIProcessUserContentWebUserContentControllerProxycpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit2/UIProcess/UserContent/WebUserContentControllerProxy.cpp (197171 => 197172)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/UIProcess/UserContent/WebUserContentControllerProxy.cpp        2016-02-26 17:36:41 UTC (rev 197171)
+++ trunk/Source/WebKit2/UIProcess/UserContent/WebUserContentControllerProxy.cpp        2016-02-26 17:50:50 UTC (rev 197172)
</span><span class="lines">@@ -27,6 +27,7 @@
</span><span class="cx"> #include &quot;WebUserContentControllerProxy.h&quot;
</span><span class="cx"> 
</span><span class="cx"> #include &quot;APIArray.h&quot;
</span><ins>+#include &quot;APIUserContentWorld.h&quot;
</ins><span class="cx"> #include &quot;APIUserScript.h&quot;
</span><span class="cx"> #include &quot;APIUserStyleSheet.h&quot;
</span><span class="cx"> #include &quot;DataReference.h&quot;
</span><span class="lines">@@ -74,9 +75,14 @@
</span><span class="cx"> 
</span><span class="cx">     webProcessProxy.addMessageReceiver(Messages::WebUserContentControllerProxy::messageReceiverName(), m_identifier, *this);
</span><span class="cx"> 
</span><del>-    Vector&lt;WebCore::UserScript&gt; userScripts;
</del><ins>+    Vector&lt;std::pair&lt;uint64_t, String&gt;&gt; userContentWorlds;
+    for (const auto&amp; world : m_userContentWorlds)
+        userContentWorlds.append(std::make_pair(world.key-&gt;identifier(), world.key-&gt;name()));
+    webProcessProxy.connection()-&gt;send(Messages::WebUserContentController::AddUserContentWorlds(userContentWorlds), m_identifier);
+
+    Vector&lt;std::pair&lt;uint64_t, WebCore::UserScript&gt;&gt; userScripts;
</ins><span class="cx">     for (const auto&amp; userScript : m_userScripts-&gt;elementsOfType&lt;API::UserScript&gt;())
</span><del>-        userScripts.append(userScript-&gt;userScript());
</del><ins>+        userScripts.append(std::make_pair(userScript-&gt;userContentWorld().identifier(), userScript-&gt;userScript()));
</ins><span class="cx">     webProcessProxy.connection()-&gt;send(Messages::WebUserContentController::AddUserScripts(userScripts), m_identifier);
</span><span class="cx"> 
</span><span class="cx">     Vector&lt;WebCore::UserStyleSheet&gt; userStyleSheets;
</span><span class="lines">@@ -107,26 +113,45 @@
</span><span class="cx"> 
</span><span class="cx"> void WebUserContentControllerProxy::addUserScript(API::UserScript&amp; userScript)
</span><span class="cx"> {
</span><ins>+    Ref&lt;API::UserContentWorld&gt; world = userScript.userContentWorld();
+
+    if (world.ptr() != &amp;API::UserContentWorld::normalWorld()) {
+        auto addResult = m_userContentWorlds.add(world.ptr());
+        if (addResult.isNewEntry) {
+            for (WebProcessProxy* process : m_processes)
+                process-&gt;connection()-&gt;send(Messages::WebUserContentController::AddUserContentWorlds({ std::make_pair(world-&gt;identifier(), world-&gt;name()) }), m_identifier);
+        }
+    }
+
</ins><span class="cx">     m_userScripts-&gt;elements().append(&amp;userScript);
</span><span class="cx"> 
</span><span class="cx">     for (WebProcessProxy* process : m_processes)
</span><del>-        process-&gt;connection()-&gt;send(Messages::WebUserContentController::AddUserScripts({ userScript.userScript() }), m_identifier);
</del><ins>+        process-&gt;connection()-&gt;send(Messages::WebUserContentController::AddUserScripts({ std::make_pair(world-&gt;identifier(), userScript.userScript()) }), m_identifier);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><del>-void WebUserContentControllerProxy::removeUserScript(const API::UserScript&amp; userScript)
</del><ins>+void WebUserContentControllerProxy::removeUserScript(API::UserScript&amp; userScript)
</ins><span class="cx"> {
</span><ins>+    Ref&lt;API::UserContentWorld&gt; world = userScript.userContentWorld();
+
</ins><span class="cx">     for (WebProcessProxy* process : m_processes)
</span><del>-        process-&gt;connection()-&gt;send(Messages::WebUserContentController::RemoveUserScript({ userScript.userScript().url().string() }), m_identifier);
</del><ins>+        process-&gt;connection()-&gt;send(Messages::WebUserContentController::RemoveUserScript(world-&gt;identifier(), userScript.userScript().url().string()), m_identifier);
</ins><span class="cx"> 
</span><span class="cx">     m_userScripts-&gt;elements().removeAll(&amp;userScript);
</span><ins>+
+    if (world.ptr() != &amp;API::UserContentWorld::normalWorld()) {
+        if (m_userContentWorlds.remove(&amp;userScript.userContentWorld())) {
+            for (WebProcessProxy* process : m_processes)
+                process-&gt;connection()-&gt;send(Messages::WebUserContentController::RemoveUserContentWorld(world-&gt;identifier()), m_identifier);
+        }
+    }
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void WebUserContentControllerProxy::removeAllUserScripts()
</span><span class="cx"> {
</span><ins>+    for (WebProcessProxy* process : m_processes)
+        process-&gt;connection()-&gt;send(Messages::WebUserContentController::RemoveAllUserScripts(API::UserContentWorld::normalWorld().identifier()), m_identifier);
+
</ins><span class="cx">     m_userScripts-&gt;elements().clear();
</span><del>-
-    for (WebProcessProxy* process : m_processes)
-        process-&gt;connection()-&gt;send(Messages::WebUserContentController::RemoveAllUserScripts(), m_identifier);
</del><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> void WebUserContentControllerProxy::addUserStyleSheet(API::UserStyleSheet&amp; userStyleSheet)
</span></span></pre></div>
<a id="trunkSourceWebKit2UIProcessUserContentWebUserContentControllerProxyh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit2/UIProcess/UserContent/WebUserContentControllerProxy.h (197171 => 197172)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/UIProcess/UserContent/WebUserContentControllerProxy.h        2016-02-26 17:36:41 UTC (rev 197171)
+++ trunk/Source/WebKit2/UIProcess/UserContent/WebUserContentControllerProxy.h        2016-02-26 17:50:50 UTC (rev 197172)
</span><span class="lines">@@ -29,6 +29,7 @@
</span><span class="cx"> #include &quot;APIObject.h&quot;
</span><span class="cx"> #include &quot;MessageReceiver.h&quot;
</span><span class="cx"> #include &lt;wtf/Forward.h&gt;
</span><ins>+#include &lt;wtf/HashCountedSet.h&gt;
</ins><span class="cx"> #include &lt;wtf/HashMap.h&gt;
</span><span class="cx"> #include &lt;wtf/HashSet.h&gt;
</span><span class="cx"> #include &lt;wtf/PassRefPtr.h&gt;
</span><span class="lines">@@ -39,6 +40,7 @@
</span><span class="cx"> 
</span><span class="cx"> namespace API {
</span><span class="cx"> class Array;
</span><ins>+class UserContentWorld;
</ins><span class="cx"> class UserContentExtension;
</span><span class="cx"> class UserScript;
</span><span class="cx"> class UserStyleSheet;
</span><span class="lines">@@ -73,7 +75,7 @@
</span><span class="cx"> 
</span><span class="cx">     API::Array&amp; userScripts() { return m_userScripts.get(); }
</span><span class="cx">     void addUserScript(API::UserScript&amp;);
</span><del>-    void removeUserScript(const API::UserScript&amp;);
</del><ins>+    void removeUserScript(API::UserScript&amp;);
</ins><span class="cx">     void removeAllUserScripts();
</span><span class="cx"> 
</span><span class="cx">     API::Array&amp; userStyleSheets() { return m_userStyleSheets.get(); }
</span><span class="lines">@@ -102,6 +104,7 @@
</span><span class="cx">     Ref&lt;API::Array&gt; m_userScripts;
</span><span class="cx">     Ref&lt;API::Array&gt; m_userStyleSheets;
</span><span class="cx">     HashMap&lt;uint64_t, RefPtr&lt;WebScriptMessageHandler&gt;&gt; m_scriptMessageHandlers;
</span><ins>+    HashCountedSet&lt;RefPtr&lt;API::UserContentWorld&gt;&gt; m_userContentWorlds;
</ins><span class="cx"> 
</span><span class="cx"> #if ENABLE(CONTENT_EXTENSIONS)
</span><span class="cx">     HashMap&lt;String, RefPtr&lt;API::UserContentExtension&gt;&gt; m_userContentExtensions;
</span></span></pre></div>
<a id="trunkSourceWebKit2WebKit2xcodeprojprojectpbxproj"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit2/WebKit2.xcodeproj/project.pbxproj (197171 => 197172)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/WebKit2.xcodeproj/project.pbxproj        2016-02-26 17:36:41 UTC (rev 197171)
+++ trunk/Source/WebKit2/WebKit2.xcodeproj/project.pbxproj        2016-02-26 17:50:50 UTC (rev 197172)
</span><span class="lines">@@ -1074,6 +1074,12 @@
</span><span class="cx">                 7C85FD7C193415A8000177C4 /* WebPreferencesDefinitions.h in Headers */ = {isa = PBXBuildFile; fileRef = 7C85FD7B193415A8000177C4 /* WebPreferencesDefinitions.h */; };
</span><span class="cx">                 7C85FD7F19341665000177C4 /* WebPreferencesKeys.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 7C85FD7D19341665000177C4 /* WebPreferencesKeys.cpp */; };
</span><span class="cx">                 7C85FD8019341665000177C4 /* WebPreferencesKeys.h in Headers */ = {isa = PBXBuildFile; fileRef = 7C85FD7E19341665000177C4 /* WebPreferencesKeys.h */; };
</span><ins>+                7C882DF71C7E9965006BF731 /* _WKUserContentWorld.h in Headers */ = {isa = PBXBuildFile; fileRef = 7C882DF31C7E995E006BF731 /* _WKUserContentWorld.h */; settings = {ATTRIBUTES = (Private, ); }; };
+                7C882DF81C7E996C006BF731 /* _WKUserContentWorld.mm in Sources */ = {isa = PBXBuildFile; fileRef = 7C882DF41C7E995E006BF731 /* _WKUserContentWorld.mm */; };
+                7C882DF91C7E996F006BF731 /* _WKUserContentWorldInternal.h in Headers */ = {isa = PBXBuildFile; fileRef = 7C882DF51C7E995E006BF731 /* _WKUserContentWorldInternal.h */; };
+                7C882DFA1C7E9973006BF731 /* WKUserScriptPrivate.h in Headers */ = {isa = PBXBuildFile; fileRef = 7C882DF61C7E995E006BF731 /* WKUserScriptPrivate.h */; settings = {ATTRIBUTES = (Private, ); }; };
+                7C882DFD1C7E99A8006BF731 /* APIUserContentWorld.h in Headers */ = {isa = PBXBuildFile; fileRef = 7C882DFC1C7E99A6006BF731 /* APIUserContentWorld.h */; };
+                7C882DFE1C7E99AC006BF731 /* APIUserContentWorld.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 7C882DFB1C7E99A6006BF731 /* APIUserContentWorld.cpp */; };
</ins><span class="cx">                 7C89D2941A67122F003A5FDE /* APIUserScript.h in Headers */ = {isa = PBXBuildFile; fileRef = 7C89D2921A67122F003A5FDE /* APIUserScript.h */; };
</span><span class="cx">                 7C89D2971A6753B2003A5FDE /* APIPageConfiguration.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 7C89D2951A6753B2003A5FDE /* APIPageConfiguration.cpp */; };
</span><span class="cx">                 7C89D2981A6753B2003A5FDE /* APIPageConfiguration.h in Headers */ = {isa = PBXBuildFile; fileRef = 7C89D2961A6753B2003A5FDE /* APIPageConfiguration.h */; };
</span><span class="lines">@@ -3076,6 +3082,12 @@
</span><span class="cx">                 7C85FD7B193415A8000177C4 /* WebPreferencesDefinitions.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = WebPreferencesDefinitions.h; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="cx">                 7C85FD7D19341665000177C4 /* WebPreferencesKeys.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = WebPreferencesKeys.cpp; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="cx">                 7C85FD7E19341665000177C4 /* WebPreferencesKeys.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = WebPreferencesKeys.h; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><ins>+                7C882DF31C7E995E006BF731 /* _WKUserContentWorld.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = _WKUserContentWorld.h; sourceTree = &quot;&lt;group&gt;&quot;; };
+                7C882DF41C7E995E006BF731 /* _WKUserContentWorld.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = _WKUserContentWorld.mm; sourceTree = &quot;&lt;group&gt;&quot;; };
+                7C882DF51C7E995E006BF731 /* _WKUserContentWorldInternal.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = _WKUserContentWorldInternal.h; sourceTree = &quot;&lt;group&gt;&quot;; };
+                7C882DF61C7E995E006BF731 /* WKUserScriptPrivate.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = WKUserScriptPrivate.h; sourceTree = &quot;&lt;group&gt;&quot;; };
+                7C882DFB1C7E99A6006BF731 /* APIUserContentWorld.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = APIUserContentWorld.cpp; sourceTree = &quot;&lt;group&gt;&quot;; };
+                7C882DFC1C7E99A6006BF731 /* APIUserContentWorld.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = APIUserContentWorld.h; sourceTree = &quot;&lt;group&gt;&quot;; };
</ins><span class="cx">                 7C89D2921A67122F003A5FDE /* APIUserScript.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = APIUserScript.h; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="cx">                 7C89D2951A6753B2003A5FDE /* APIPageConfiguration.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = APIPageConfiguration.cpp; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="cx">                 7C89D2961A6753B2003A5FDE /* APIPageConfiguration.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = APIPageConfiguration.h; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="lines">@@ -4968,6 +4980,9 @@
</span><span class="cx">                                 7C89D2B81A6B0F2C003A5FDE /* _WKUserContentFilter.h */,
</span><span class="cx">                                 7C89D2B71A6B0F2C003A5FDE /* _WKUserContentFilter.mm */,
</span><span class="cx">                                 7C89D2BB1A6B0F5B003A5FDE /* _WKUserContentFilterInternal.h */,
</span><ins>+                                7C882DF31C7E995E006BF731 /* _WKUserContentWorld.h */,
+                                7C882DF41C7E995E006BF731 /* _WKUserContentWorld.mm */,
+                                7C882DF51C7E995E006BF731 /* _WKUserContentWorldInternal.h */,
</ins><span class="cx">                                 2D87861B1BDB54BF00D02ABB /* _WKUserStyleSheet.h */,
</span><span class="cx">                                 2D87861C1BDB54BF00D02ABB /* _WKUserStyleSheet.mm */,
</span><span class="cx">                                 2D87861F1BDB57F500D02ABB /* _WKUserStyleSheetInternal.h */,
</span><span class="lines">@@ -5034,6 +5049,7 @@
</span><span class="cx">                                 1AAF089919267EE500B6390C /* WKUserScript.h */,
</span><span class="cx">                                 1AAF089819267EE500B6390C /* WKUserScript.mm */,
</span><span class="cx">                                 1AAF089C19267FC800B6390C /* WKUserScriptInternal.h */,
</span><ins>+                                7C882DF61C7E995E006BF731 /* WKUserScriptPrivate.h */,
</ins><span class="cx">                                 1A4832CA1A9BC465008B4DFE /* WKWebsiteDataRecord.h */,
</span><span class="cx">                                 1A4832C91A9BC465008B4DFE /* WKWebsiteDataRecord.mm */,
</span><span class="cx">                                 1A4832CD1A9BC484008B4DFE /* WKWebsiteDataRecordInternal.h */,
</span><span class="lines">@@ -5928,6 +5944,8 @@
</span><span class="cx">                                 7C89D2B21A6B068C003A5FDE /* APIUserContentExtension.h */,
</span><span class="cx">                                 7C3A06A51AAB903E009D74BA /* APIUserContentExtensionStore.cpp */,
</span><span class="cx">                                 7C3A06A61AAB903E009D74BA /* APIUserContentExtensionStore.h */,
</span><ins>+                                7C882DFB1C7E99A6006BF731 /* APIUserContentWorld.cpp */,
+                                7C882DFC1C7E99A6006BF731 /* APIUserContentWorld.h */,
</ins><span class="cx">                                 7C89D2A51A6789EA003A5FDE /* APIUserScript.cpp */,
</span><span class="cx">                                 7C89D2921A67122F003A5FDE /* APIUserScript.h */,
</span><span class="cx">                                 2D8786211BDB58FF00D02ABB /* APIUserStyleSheet.cpp */,
</span><span class="lines">@@ -7151,6 +7169,7 @@
</span><span class="cx">                                 1A3DD206125E5A2F004515E6 /* APIClient.h in Headers */,
</span><span class="cx">                                 076E884E1A13CADF005E90FC /* APIContextMenuClient.h in Headers */,
</span><span class="cx">                                 51578B831209ECEF00A37C4A /* APIData.h in Headers */,
</span><ins>+                                7C882DF91C7E996F006BF731 /* _WKUserContentWorldInternal.h in Headers */,
</ins><span class="cx">                                 83891B631A68B3420030F386 /* APIDiagnosticLoggingClient.h in Headers */,
</span><span class="cx">                                 7C1BA33E1A4A0E600043E249 /* APIDictionary.h in Headers */,
</span><span class="cx">                                 1F7D36C118DA513F00D9D659 /* APIDownloadClient.h in Headers */,
</span><span class="lines">@@ -7506,6 +7525,7 @@
</span><span class="cx">                                 CEDA12E3152CD1B300D9E08D /* WebAlternativeTextClient.h in Headers */,
</span><span class="cx">                                 BC72BA1E11E64907001EB4EA /* WebBackForwardList.h in Headers */,
</span><span class="cx">                                 518D2CAE12D5153B003BB93B /* WebBackForwardListItem.h in Headers */,
</span><ins>+                                7C882DFD1C7E99A8006BF731 /* APIUserContentWorld.h in Headers */,
</ins><span class="cx">                                 BC72B9FB11E6476B001EB4EA /* WebBackForwardListProxy.h in Headers */,
</span><span class="cx">                                 BCF50728124329AA005955AE /* WebCertificateInfo.h in Headers */,
</span><span class="cx">                                 BC032D7510F4378D0058C15A /* WebChromeClient.h in Headers */,
</span><span class="lines">@@ -7646,6 +7666,7 @@
</span><span class="cx">                                 512F589D12A8838800629530 /* WebProtectionSpace.h in Headers */,
</span><span class="cx">                                 A1C512C9190656E500448914 /* WebQuickLookHandleClient.h in Headers */,
</span><span class="cx">                                 37948404150C350600E52CE9 /* WebRenderLayer.h in Headers */,
</span><ins>+                                7C882DF71C7E9965006BF731 /* _WKUserContentWorld.h in Headers */,
</ins><span class="cx">                                 3760881F150413E900FC82C7 /* WebRenderObject.h in Headers */,
</span><span class="cx">                                 510AFFBA16542048001BA05E /* WebResourceLoader.h in Headers */,
</span><span class="cx">                                 51F060E01654317F00F3281B /* WebResourceLoaderMessages.h in Headers */,
</span><span class="lines">@@ -7684,6 +7705,7 @@
</span><span class="cx">                                 37C4C08D1814AC5C003688B9 /* WKBackForwardList.h in Headers */,
</span><span class="cx">                                 37C4C0951814B9E6003688B9 /* WKBackForwardListInternal.h in Headers */,
</span><span class="cx">                                 510523701C739D42007993CB /* WebIDBConnectionToClient.h in Headers */,
</span><ins>+                                7C882DFA1C7E9973006BF731 /* WKUserScriptPrivate.h in Headers */,
</ins><span class="cx">                                 37C4C08718149C5B003688B9 /* WKBackForwardListItem.h in Headers */,
</span><span class="cx">                                 37C4C08918149F23003688B9 /* WKBackForwardListItemInternal.h in Headers */,
</span><span class="cx">                                 BC646C1D11DD399F006455B0 /* WKBackForwardListItemRef.h in Headers */,
</span><span class="lines">@@ -8844,6 +8866,7 @@
</span><span class="cx">                                 31A67E0C165B2A99006CBA66 /* PlugInAutoStartProvider.cpp in Sources */,
</span><span class="cx">                                 1A8EF4CC1252403700F7067F /* PluginControllerProxy.cpp in Sources */,
</span><span class="cx">                                 1A2D91A61281D739001EB962 /* PluginControllerProxyMac.mm in Sources */,
</span><ins>+                                7C882DFE1C7E99AC006BF731 /* APIUserContentWorld.cpp in Sources */,
</ins><span class="cx">                                 1A8EF96E1252AF6B00F7067F /* PluginControllerProxyMessageReceiver.cpp in Sources */,
</span><span class="cx">                                 1A17977F137EE82C00F97D45 /* PluginCreationParameters.cpp in Sources */,
</span><span class="cx">                                 7C3F8C90173AF52D007B7F39 /* PluginInformation.cpp in Sources */,
</span><span class="lines">@@ -8889,6 +8912,7 @@
</span><span class="cx">                                 1AB16AE11648656D00290D62 /* RemoteLayerTreeDrawingAreaProxy.mm in Sources */,
</span><span class="cx">                                 0FF24A2D1879E4BC003ABF0C /* RemoteLayerTreeDrawingAreaProxyMessageReceiver.cpp in Sources */,
</span><span class="cx">                                 1AA3D75B1651B44F008713D0 /* RemoteLayerTreeHost.mm in Sources */,
</span><ins>+                                7C882DF81C7E996C006BF731 /* _WKUserContentWorld.mm in Sources */,
</ins><span class="cx">                                 0F0C365818C051BA00F607D7 /* RemoteLayerTreeHostIOS.mm in Sources */,
</span><span class="cx">                                 2DDE0AFB18298CC900F97EAA /* RemoteLayerTreePropertyApplier.mm in Sources */,
</span><span class="cx">                                 0FF2649F1A1FF9C6001FE759 /* RemoteLayerTreeScrollingPerformanceData.mm in Sources */,
</span></span></pre></div>
<a id="trunkSourceWebKit2WebProcessInjectedBundleAPICocoaWKWebProcessPlugInScriptWorldh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit2/WebProcess/InjectedBundle/API/Cocoa/WKWebProcessPlugInScriptWorld.h (197171 => 197172)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/WebProcess/InjectedBundle/API/Cocoa/WKWebProcessPlugInScriptWorld.h        2016-02-26 17:36:41 UTC (rev 197171)
+++ trunk/Source/WebKit2/WebProcess/InjectedBundle/API/Cocoa/WKWebProcessPlugInScriptWorld.h        2016-02-26 17:50:50 UTC (rev 197172)
</span><span class="lines">@@ -35,6 +35,8 @@
</span><span class="cx"> + (WKWebProcessPlugInScriptWorld *)world;
</span><span class="cx"> + (WKWebProcessPlugInScriptWorld *)normalWorld;
</span><span class="cx"> 
</span><ins>+@property (nonatomic, readonly, copy) NSString *name;
+
</ins><span class="cx"> - (void)clearWrappers;
</span><span class="cx"> 
</span><span class="cx"> @end
</span></span></pre></div>
<a id="trunkSourceWebKit2WebProcessInjectedBundleAPICocoaWKWebProcessPlugInScriptWorldmm"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit2/WebProcess/InjectedBundle/API/Cocoa/WKWebProcessPlugInScriptWorld.mm (197171 => 197172)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/WebProcess/InjectedBundle/API/Cocoa/WKWebProcessPlugInScriptWorld.mm        2016-02-26 17:36:41 UTC (rev 197171)
+++ trunk/Source/WebKit2/WebProcess/InjectedBundle/API/Cocoa/WKWebProcessPlugInScriptWorld.mm        2016-02-26 17:50:50 UTC (rev 197172)
</span><span class="lines">@@ -56,6 +56,11 @@
</span><span class="cx">     _world-&gt;clearWrappers();
</span><span class="cx"> }
</span><span class="cx"> 
</span><ins>+- (NSString *)name
+{
+    return _world-&gt;name();
+}
+
</ins><span class="cx"> - (InjectedBundleScriptWorld&amp;)_scriptWorld
</span><span class="cx"> {
</span><span class="cx">     return *_world;
</span></span></pre></div>
<a id="trunkSourceWebKit2WebProcessInjectedBundleAPIcWKBundleScriptWorldcpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit2/WebProcess/InjectedBundle/API/c/WKBundleScriptWorld.cpp (197171 => 197172)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/WebProcess/InjectedBundle/API/c/WKBundleScriptWorld.cpp        2016-02-26 17:36:41 UTC (rev 197171)
+++ trunk/Source/WebKit2/WebProcess/InjectedBundle/API/c/WKBundleScriptWorld.cpp        2016-02-26 17:50:50 UTC (rev 197172)
</span><span class="lines">@@ -57,3 +57,8 @@
</span><span class="cx"> {
</span><span class="cx">     toImpl(scriptWorldRef)-&gt;makeAllShadowRootsOpen();
</span><span class="cx"> }
</span><ins>+
+WKStringRef WKBundleScriptWorldCopyName(WKBundleScriptWorldRef scriptWorldRef)
+{
+    return toCopiedAPI(toImpl(scriptWorldRef)-&gt;name());
+}
</ins></span></pre></div>
<a id="trunkSourceWebKit2WebProcessInjectedBundleAPIcWKBundleScriptWorldh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit2/WebProcess/InjectedBundle/API/c/WKBundleScriptWorld.h (197171 => 197172)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/WebProcess/InjectedBundle/API/c/WKBundleScriptWorld.h        2016-02-26 17:36:41 UTC (rev 197171)
+++ trunk/Source/WebKit2/WebProcess/InjectedBundle/API/c/WKBundleScriptWorld.h        2016-02-26 17:50:50 UTC (rev 197172)
</span><span class="lines">@@ -38,6 +38,7 @@
</span><span class="cx"> WK_EXPORT WKBundleScriptWorldRef WKBundleScriptWorldNormalWorld();
</span><span class="cx"> WK_EXPORT void WKBundleScriptWorldClearWrappers(WKBundleScriptWorldRef scriptWorld);
</span><span class="cx"> WK_EXPORT void WKBundleScriptWorldMakeAllShadowRootsOpen(WKBundleScriptWorldRef scriptWorld);
</span><ins>+WK_EXPORT WKStringRef WKBundleScriptWorldCopyName(WKBundleScriptWorldRef scriptWorld);
</ins><span class="cx"> 
</span><span class="cx"> #ifdef __cplusplus
</span><span class="cx"> }
</span></span></pre></div>
<a id="trunkSourceWebKit2WebProcessInjectedBundleInjectedBundleScriptWorldcpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit2/WebProcess/InjectedBundle/InjectedBundleScriptWorld.cpp (197171 => 197172)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/WebProcess/InjectedBundle/InjectedBundleScriptWorld.cpp        2016-02-26 17:36:41 UTC (rev 197171)
+++ trunk/Source/WebKit2/WebProcess/InjectedBundle/InjectedBundleScriptWorld.cpp        2016-02-26 17:50:50 UTC (rev 197172)
</span><span class="lines">@@ -30,6 +30,8 @@
</span><span class="cx"> #include &lt;WebCore/ScriptController.h&gt;
</span><span class="cx"> #include &lt;wtf/HashMap.h&gt;
</span><span class="cx"> #include &lt;wtf/NeverDestroyed.h&gt;
</span><ins>+#include &lt;wtf/text/StringConcatenate.h&gt;
+#include &lt;wtf/text/WTFString.h&gt;
</ins><span class="cx"> 
</span><span class="cx"> using namespace WebCore;
</span><span class="cx"> 
</span><span class="lines">@@ -43,11 +45,22 @@
</span><span class="cx">     return map;
</span><span class="cx"> }
</span><span class="cx"> 
</span><ins>+static String uniqueWorldName()
+{
+    static uint64_t uniqueWorldNameNumber = 0;
+    return makeString(ASCIILiteral(&quot;UniqueWorld_&quot;), String::number(uniqueWorldNameNumber++));
+}
+
</ins><span class="cx"> Ref&lt;InjectedBundleScriptWorld&gt; InjectedBundleScriptWorld::create()
</span><span class="cx"> {
</span><del>-    return adoptRef(*new InjectedBundleScriptWorld(ScriptController::createWorld()));
</del><ins>+    return adoptRef(*new InjectedBundleScriptWorld(ScriptController::createWorld(), uniqueWorldName()));
</ins><span class="cx"> }
</span><span class="cx"> 
</span><ins>+Ref&lt;InjectedBundleScriptWorld&gt; InjectedBundleScriptWorld::create(const String&amp; name)
+{
+    return adoptRef(*new InjectedBundleScriptWorld(ScriptController::createWorld(), name));
+}
+
</ins><span class="cx"> PassRefPtr&lt;InjectedBundleScriptWorld&gt; InjectedBundleScriptWorld::getOrCreate(DOMWrapperWorld&amp; world)
</span><span class="cx"> {
</span><span class="cx">     if (&amp;world == &amp;mainThreadNormalWorld())
</span><span class="lines">@@ -56,32 +69,38 @@
</span><span class="cx">     if (InjectedBundleScriptWorld* existingWorld = allWorlds().get(&amp;world))
</span><span class="cx">         return existingWorld;
</span><span class="cx"> 
</span><del>-    return adoptRef(new InjectedBundleScriptWorld(&amp;world));
</del><ins>+    return adoptRef(new InjectedBundleScriptWorld(world, uniqueWorldName()));
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> InjectedBundleScriptWorld* InjectedBundleScriptWorld::normalWorld()
</span><span class="cx"> {
</span><del>-    static InjectedBundleScriptWorld* world = adoptRef(new InjectedBundleScriptWorld(&amp;mainThreadNormalWorld())).leakRef();
</del><ins>+    static InjectedBundleScriptWorld* world = adoptRef(new InjectedBundleScriptWorld(mainThreadNormalWorld(), String())).leakRef();
</ins><span class="cx">     return world;
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-InjectedBundleScriptWorld::InjectedBundleScriptWorld(PassRefPtr&lt;DOMWrapperWorld&gt; world)
</del><ins>+InjectedBundleScriptWorld::InjectedBundleScriptWorld(DOMWrapperWorld&amp; world, const String&amp; name)
</ins><span class="cx">     : m_world(world)
</span><ins>+    , m_name(name)
</ins><span class="cx"> {
</span><del>-    ASSERT(!allWorlds().contains(m_world.get()));
-    allWorlds().add(m_world.get(), this);
</del><ins>+    ASSERT(!allWorlds().contains(m_world.ptr()));
+    allWorlds().add(m_world.ptr(), this);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> InjectedBundleScriptWorld::~InjectedBundleScriptWorld()
</span><span class="cx"> {
</span><del>-    ASSERT(allWorlds().contains(m_world.get()));
-    allWorlds().remove(m_world.get());
</del><ins>+    ASSERT(allWorlds().contains(m_world.ptr()));
+    allWorlds().remove(m_world.ptr());
</ins><span class="cx"> }
</span><span class="cx"> 
</span><del>-DOMWrapperWorld&amp; InjectedBundleScriptWorld::coreWorld() const
</del><ins>+const DOMWrapperWorld&amp; InjectedBundleScriptWorld::coreWorld() const
</ins><span class="cx"> {
</span><del>-    return *m_world.get();
</del><ins>+    return m_world;
</ins><span class="cx"> }
</span><ins>+
+DOMWrapperWorld&amp; InjectedBundleScriptWorld::coreWorld()
+{
+    return m_world;
+}
</ins><span class="cx">     
</span><span class="cx"> void InjectedBundleScriptWorld::clearWrappers()
</span><span class="cx"> {
</span></span></pre></div>
<a id="trunkSourceWebKit2WebProcessInjectedBundleInjectedBundleScriptWorldh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit2/WebProcess/InjectedBundle/InjectedBundleScriptWorld.h (197171 => 197172)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/WebProcess/InjectedBundle/InjectedBundleScriptWorld.h        2016-02-26 17:36:41 UTC (rev 197171)
+++ trunk/Source/WebKit2/WebProcess/InjectedBundle/InjectedBundleScriptWorld.h        2016-02-26 17:50:50 UTC (rev 197172)
</span><span class="lines">@@ -29,6 +29,7 @@
</span><span class="cx"> #include &quot;APIObject.h&quot;
</span><span class="cx"> #include &lt;wtf/PassRefPtr.h&gt;
</span><span class="cx"> #include &lt;wtf/RefPtr.h&gt;
</span><ins>+#include &lt;wtf/text/WTFString.h&gt;
</ins><span class="cx"> 
</span><span class="cx"> namespace WebCore {
</span><span class="cx">     class DOMWrapperWorld;
</span><span class="lines">@@ -39,20 +40,25 @@
</span><span class="cx"> class InjectedBundleScriptWorld : public API::ObjectImpl&lt;API::Object::Type::BundleScriptWorld&gt; {
</span><span class="cx"> public:
</span><span class="cx">     static Ref&lt;InjectedBundleScriptWorld&gt; create();
</span><ins>+    static Ref&lt;InjectedBundleScriptWorld&gt; create(const String&amp;);
</ins><span class="cx">     static PassRefPtr&lt;InjectedBundleScriptWorld&gt; getOrCreate(WebCore::DOMWrapperWorld&amp;);
</span><span class="cx">     static InjectedBundleScriptWorld* normalWorld();
</span><span class="cx"> 
</span><span class="cx">     virtual ~InjectedBundleScriptWorld();
</span><span class="cx"> 
</span><del>-    WebCore::DOMWrapperWorld&amp; coreWorld() const;
</del><ins>+    const WebCore::DOMWrapperWorld&amp; coreWorld() const;
+    WebCore::DOMWrapperWorld&amp; coreWorld();
</ins><span class="cx"> 
</span><span class="cx">     void clearWrappers();
</span><span class="cx">     void makeAllShadowRootsOpen();
</span><span class="cx"> 
</span><ins>+    const String&amp; name() const { return m_name; }
+
</ins><span class="cx"> private:
</span><del>-    InjectedBundleScriptWorld(PassRefPtr&lt;WebCore::DOMWrapperWorld&gt;);
</del><ins>+    InjectedBundleScriptWorld(WebCore::DOMWrapperWorld&amp;, const String&amp;);
</ins><span class="cx"> 
</span><del>-    RefPtr&lt;WebCore::DOMWrapperWorld&gt; m_world;
</del><ins>+    Ref&lt;WebCore::DOMWrapperWorld&gt; m_world;
+    String m_name;
</ins><span class="cx"> };
</span><span class="cx"> 
</span><span class="cx"> } // namespace WebKit
</span></span></pre></div>
<a id="trunkSourceWebKit2WebProcessUserContentWebUserContentControllercpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit2/WebProcess/UserContent/WebUserContentController.cpp (197171 => 197172)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/WebProcess/UserContent/WebUserContentController.cpp        2016-02-26 17:36:41 UTC (rev 197171)
+++ trunk/Source/WebKit2/WebProcess/UserContent/WebUserContentController.cpp        2016-02-26 17:50:50 UTC (rev 197172)
</span><span class="lines">@@ -27,6 +27,7 @@
</span><span class="cx"> #include &quot;WebUserContentController.h&quot;
</span><span class="cx"> 
</span><span class="cx"> #include &quot;DataReference.h&quot;
</span><ins>+#include &quot;InjectedBundleScriptWorld.h&quot;
</ins><span class="cx"> #include &quot;WebCompiledContentExtension.h&quot;
</span><span class="cx"> #include &quot;WebFrame.h&quot;
</span><span class="cx"> #include &quot;WebPage.h&quot;
</span><span class="lines">@@ -56,6 +57,15 @@
</span><span class="cx">     return userContentControllers;
</span><span class="cx"> }
</span><span class="cx"> 
</span><ins>+typedef HashMap&lt;uint64_t, std::pair&lt;RefPtr&lt;InjectedBundleScriptWorld&gt;, unsigned&gt;&gt; WorldMap;
+
+static WorldMap&amp; worldMap()
+{
+    static NeverDestroyed&lt;WorldMap&gt; map(std::initializer_list&lt;WorldMap::KeyValuePairType&gt; { { 1, std::make_pair(InjectedBundleScriptWorld::normalWorld(), 1) } });
+
+    return map;
+}
+
</ins><span class="cx"> PassRefPtr&lt;WebUserContentController&gt; WebUserContentController::getOrCreate(uint64_t identifier)
</span><span class="cx"> {
</span><span class="cx">     auto&amp; userContentControllerPtr = userContentControllers().add(identifier, nullptr).iterator-&gt;value;
</span><span class="lines">@@ -84,22 +94,69 @@
</span><span class="cx">     userContentControllers().remove(m_identifier);
</span><span class="cx"> }
</span><span class="cx"> 
</span><del>-void WebUserContentController::addUserScripts(const Vector&lt;WebCore::UserScript&gt;&amp; userScripts)
</del><ins>+
+void WebUserContentController::addUserContentWorlds(const Vector&lt;std::pair&lt;uint64_t, String&gt;&gt;&amp; worlds)
</ins><span class="cx"> {
</span><del>-    for (const auto&amp; userScript : userScripts)
-        m_userContentController-&gt;addUserScript(mainThreadNormalWorld(), std::make_unique&lt;WebCore::UserScript&gt;(userScript));
</del><ins>+    for (auto&amp; world : worlds) {
+        ASSERT(world.first);
+        ASSERT(world.first != 1);
+
+        worldMap().ensure(world.first, [&amp;] { return std::make_pair(InjectedBundleScriptWorld::create(world.second), 1); });
+    }
</ins><span class="cx"> }
</span><span class="cx"> 
</span><del>-void WebUserContentController::removeUserScript(const String&amp; urlString)
</del><ins>+void WebUserContentController::removeUserContentWorld(uint64_t worldIdentifier)
</ins><span class="cx"> {
</span><del>-    m_userContentController-&gt;removeUserScript(mainThreadNormalWorld(), URL(URL(), urlString));
</del><ins>+    ASSERT(worldIdentifier);
+    ASSERT(worldIdentifier != 1);
+
+    auto it = worldMap().find(worldIdentifier);
+    if (it == worldMap().end()) {
+        WTFLogAlways(&quot;Trying to remove a UserContentWorld (id=%llu) that is does not exist.&quot;, worldIdentifier);
+        return;
+    }
+
+    it-&gt;value.second--;
+    
+    if (!it-&gt;value.second)
+        worldMap().remove(it);
</ins><span class="cx"> }
</span><span class="cx"> 
</span><del>-void WebUserContentController::removeAllUserScripts()
</del><ins>+void WebUserContentController::addUserScripts(const Vector&lt;std::pair&lt;uint64_t, WebCore::UserScript&gt;&gt;&amp; userScripts)
</ins><span class="cx"> {
</span><del>-    m_userContentController-&gt;removeUserScripts(mainThreadNormalWorld());
</del><ins>+    for (const auto&amp; userScriptWorldPair : userScripts) {
+        auto it = worldMap().find(userScriptWorldPair.first);
+        if (it == worldMap().end()) {
+            WTFLogAlways(&quot;Trying to add a UserScript to a UserContentWorld (id=%llu) that does not exist.&quot;, userScriptWorldPair.first);
+            continue;
+        }
+
+        m_userContentController-&gt;addUserScript(it-&gt;value.first-&gt;coreWorld(), std::make_unique&lt;WebCore::UserScript&gt;(userScriptWorldPair.second));
+    }
</ins><span class="cx"> }
</span><span class="cx"> 
</span><ins>+void WebUserContentController::removeUserScript(uint64_t worldIdentifier, const String&amp; urlString)
+{
+    auto it = worldMap().find(worldIdentifier);
+    if (it == worldMap().end()) {
+        WTFLogAlways(&quot;Trying to remove a UserScript from a UserContentWorld (id=%llu) that does not exist.&quot;, worldIdentifier);
+        return;
+    }
+
+    m_userContentController-&gt;removeUserScript(it-&gt;value.first-&gt;coreWorld(), URL(URL(), urlString));
+}
+
+void WebUserContentController::removeAllUserScripts(uint64_t worldIdentifier)
+{
+    auto it = worldMap().find(worldIdentifier);
+    if (it == worldMap().end()) {
+        WTFLogAlways(&quot;Trying to remove all UserScripts from a UserContentWorld (id=%llu) that does not exist.&quot;, worldIdentifier);
+        return;
+    }
+
+    m_userContentController-&gt;removeUserScripts(it-&gt;value.first-&gt;coreWorld());
+}
+
</ins><span class="cx"> void WebUserContentController::addUserStyleSheets(const Vector&lt;WebCore::UserStyleSheet&gt;&amp; userStyleSheets)
</span><span class="cx"> {
</span><span class="cx">     for (const auto&amp; userStyleSheet : userStyleSheets) {
</span></span></pre></div>
<a id="trunkSourceWebKit2WebProcessUserContentWebUserContentControllerh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit2/WebProcess/UserContent/WebUserContentController.h (197171 => 197172)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/WebProcess/UserContent/WebUserContentController.h        2016-02-26 17:36:41 UTC (rev 197171)
+++ trunk/Source/WebKit2/WebProcess/UserContent/WebUserContentController.h        2016-02-26 17:50:50 UTC (rev 197172)
</span><span class="lines">@@ -34,6 +34,7 @@
</span><span class="cx"> 
</span><span class="cx"> namespace WebKit {
</span><span class="cx"> 
</span><ins>+class InjectedBundleScriptWorld;
</ins><span class="cx"> class WebCompiledContentExtensionData;
</span><span class="cx"> class WebUserMessageHandlerDescriptorProxy;
</span><span class="cx"> 
</span><span class="lines">@@ -52,10 +53,13 @@
</span><span class="cx">     // IPC::MessageReceiver.
</span><span class="cx">     virtual void didReceiveMessage(IPC::Connection&amp;, IPC::MessageDecoder&amp;) override;
</span><span class="cx"> 
</span><del>-    void addUserScripts(const Vector&lt;WebCore::UserScript&gt;&amp;);
-    void removeUserScript(const String&amp; urlString);
-    void removeAllUserScripts();
</del><ins>+    void addUserContentWorlds(const Vector&lt;std::pair&lt;uint64_t, String&gt;&gt;&amp;);
+    void removeUserContentWorld(uint64_t);
</ins><span class="cx"> 
</span><ins>+    void addUserScripts(const Vector&lt;std::pair&lt;uint64_t, WebCore::UserScript&gt;&gt;&amp;);
+    void removeUserScript(uint64_t worldIdentifier, const String&amp; urlString);
+    void removeAllUserScripts(uint64_t worldIdentifier);
+
</ins><span class="cx">     void addUserStyleSheets(const Vector&lt;WebCore::UserStyleSheet&gt;&amp;);
</span><span class="cx">     void removeUserStyleSheet(const String&amp; urlString);
</span><span class="cx">     void removeAllUserStyleSheets();
</span></span></pre></div>
<a id="trunkSourceWebKit2WebProcessUserContentWebUserContentControllermessagesin"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit2/WebProcess/UserContent/WebUserContentController.messages.in (197171 => 197172)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/WebProcess/UserContent/WebUserContentController.messages.in        2016-02-26 17:36:41 UTC (rev 197171)
+++ trunk/Source/WebKit2/WebProcess/UserContent/WebUserContentController.messages.in        2016-02-26 17:50:50 UTC (rev 197172)
</span><span class="lines">@@ -24,10 +24,13 @@
</span><span class="cx">  */
</span><span class="cx"> 
</span><span class="cx"> messages -&gt; WebUserContentController {
</span><del>-    AddUserScripts(Vector&lt;WebCore::UserScript&gt; userScripts);
-    RemoveUserScript(String url);
-    RemoveAllUserScripts();
</del><ins>+    AddUserContentWorlds(Vector&lt;std::pair&lt;uint64_t, String&gt;&gt; worlds);
+    RemoveUserContentWorld(uint64_t worldIdentifier);
</ins><span class="cx"> 
</span><ins>+    AddUserScripts(Vector&lt;std::pair&lt;uint64_t, WebCore::UserScript&gt;&gt; userScripts);
+    RemoveUserScript(uint64_t worldIdentifier, String url);
+    RemoveAllUserScripts(uint64_t worldIdentifier);
+
</ins><span class="cx">     AddUserStyleSheets(Vector&lt;WebCore::UserStyleSheet&gt; userStyleSheets);
</span><span class="cx">     RemoveUserStyleSheet(String url);
</span><span class="cx">     RemoveAllUserStyleSheets();
</span></span></pre></div>
<a id="trunkToolsChangeLog"></a>
<div class="modfile"><h4>Modified: trunk/Tools/ChangeLog (197171 => 197172)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Tools/ChangeLog        2016-02-26 17:36:41 UTC (rev 197171)
+++ trunk/Tools/ChangeLog        2016-02-26 17:50:50 UTC (rev 197172)
</span><span class="lines">@@ -1,3 +1,20 @@
</span><ins>+2016-02-25  Sam Weinig  &lt;sam@webkit.org&gt;
+
+        Allow WKUserScripts to be run in isolated worlds
+        https://bugs.webkit.org/show_bug.cgi?id=154701
+
+        Reviewed by Anders Carlsson.
+
+        * TestWebKitAPI/TestWebKitAPI.xcodeproj/project.pbxproj:
+        * TestWebKitAPI/Tests/WebKit2Cocoa/_WKUserContentWorld.mm: Added.
+        (-[SimpleDelegate webView:didFinishNavigation:]):
+        (-[UserContentWorldRemoteObject didObserveNormalWorld]):
+        (-[UserContentWorldRemoteObject didObserveWorldWithName:]):
+        * TestWebKitAPI/Tests/WebKit2Cocoa/_WKUserContentWorldPlugIn.mm: Added.
+        (-[_WKUserContentWorldPlugIn webProcessPlugIn:didCreateBrowserContextController:]):
+        (-[_WKUserContentWorldPlugIn webProcessPlugInBrowserContextController:globalObjectIsAvailableForFrame:inScriptWorld:]):
+        * TestWebKitAPI/Tests/WebKit2Cocoa/_WKUserContentWorldProtocol.h: Added.
+
</ins><span class="cx"> 2016-02-26  Youenn Fablet  &lt;youenn.fablet@crf.canon.fr&gt;
</span><span class="cx"> 
</span><span class="cx">         W3C test importer should have an option to clean the destination directory
</span></span></pre></div>
<a id="trunkToolsTestWebKitAPITestWebKitAPIxcodeprojprojectpbxproj"></a>
<div class="modfile"><h4>Modified: trunk/Tools/TestWebKitAPI/TestWebKitAPI.xcodeproj/project.pbxproj (197171 => 197172)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Tools/TestWebKitAPI/TestWebKitAPI.xcodeproj/project.pbxproj        2016-02-26 17:36:41 UTC (rev 197171)
+++ trunk/Tools/TestWebKitAPI/TestWebKitAPI.xcodeproj/project.pbxproj        2016-02-26 17:50:50 UTC (rev 197172)
</span><span class="lines">@@ -91,6 +91,8 @@
</span><span class="cx">                 7C486BA11AA12567003F6F9B /* bundle-file.html in Copy Resources */ = {isa = PBXBuildFile; fileRef = 7C486BA01AA1254B003F6F9B /* bundle-file.html */; };
</span><span class="cx">                 7C54A4BE1AA11CCA00380F78 /* WKBundleFileHandle.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 7C54A4BC1AA11CCA00380F78 /* WKBundleFileHandle.cpp */; };
</span><span class="cx">                 7C54A4C11AA11CE400380F78 /* WKBundleFileHandle_Bundle.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 7C54A4BF1AA11CE400380F78 /* WKBundleFileHandle_Bundle.cpp */; };
</span><ins>+                7C882E091C80C630006BF731 /* UserContentWorldPlugIn.mm in Sources */ = {isa = PBXBuildFile; fileRef = 7C882E041C80C624006BF731 /* UserContentWorldPlugIn.mm */; };
+                7C882E0A1C80C764006BF731 /* UserContentWorld.mm in Sources */ = {isa = PBXBuildFile; fileRef = 7C882E031C80C624006BF731 /* UserContentWorld.mm */; };
</ins><span class="cx">                 7C89D2AC1A69B80D003A5FDE /* WKPageConfiguration.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 7C89D2AA1A69B80D003A5FDE /* WKPageConfiguration.cpp */; };
</span><span class="cx">                 7C9ED98B17A19F4B00E4DC33 /* attributedStringStrikethrough.html in Copy Resources */ = {isa = PBXBuildFile; fileRef = 7C9ED98A17A19D0600E4DC33 /* attributedStringStrikethrough.html */; };
</span><span class="cx">                 7CB184C61AA3F2100066EDFD /* ContentExtensions.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 7CB184C41AA3F2100066EDFD /* ContentExtensions.cpp */; };
</span><span class="lines">@@ -630,6 +632,9 @@
</span><span class="cx">                 7C6BBD8A19CEA54300C1F5E0 /* Counters.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = Counters.h; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="cx">                 7C6BBD8B19CEA63000C1F5E0 /* Counters.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = Counters.cpp; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="cx">                 7C74D42D188228F300E5ED57 /* StringView.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = StringView.cpp; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><ins>+                7C882E031C80C624006BF731 /* UserContentWorld.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = UserContentWorld.mm; sourceTree = &quot;&lt;group&gt;&quot;; };
+                7C882E041C80C624006BF731 /* UserContentWorldPlugIn.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = UserContentWorldPlugIn.mm; sourceTree = &quot;&lt;group&gt;&quot;; };
+                7C882E051C80C624006BF731 /* UserContentWorldProtocol.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = UserContentWorldProtocol.h; sourceTree = &quot;&lt;group&gt;&quot;; };
</ins><span class="cx">                 7C89D2AA1A69B80D003A5FDE /* WKPageConfiguration.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = WKPageConfiguration.cpp; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="cx">                 7C8DDAA91735DE1D00EA5AC0 /* CloseThenTerminate.cpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; path = CloseThenTerminate.cpp; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="cx">                 7C9ED98A17A19D0600E4DC33 /* attributedStringStrikethrough.html */ = {isa = PBXFileReference; lastKnownFileType = text.html; path = attributedStringStrikethrough.html; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="lines">@@ -978,6 +983,9 @@
</span><span class="cx">                                 37BCA61B1B596BA9002012CA /* ShouldOpenExternalURLsInNewWindowActions.mm */,
</span><span class="cx">                                 2D9A53AE1B31FA8D0074D5AA /* ShrinkToFit.mm */,
</span><span class="cx">                                 7CC3E1FA197E234100BE6252 /* UserContentController.mm */,
</span><ins>+                                7C882E031C80C624006BF731 /* UserContentWorld.mm */,
+                                7C882E041C80C624006BF731 /* UserContentWorldPlugIn.mm */,
+                                7C882E051C80C624006BF731 /* UserContentWorldProtocol.h */,
</ins><span class="cx">                                 2D00065D1C1F58940088E6A7 /* WKPDFViewResizeCrash.mm */,
</span><span class="cx">                                 0F3B94A51A77266C00DE3272 /* WKWebViewEvaluateJavaScript.mm */,
</span><span class="cx">                         );
</span><span class="lines">@@ -1822,6 +1830,7 @@
</span><span class="cx">                                 7CCE7ED31A411A7E00447C4C /* TypingStyleCrash.mm in Sources */,
</span><span class="cx">                                 7CCE7EDE1A411A9200447C4C /* URL.cpp in Sources */,
</span><span class="cx">                                 7CCE7EB01A411A4400447C4C /* URLExtras.mm in Sources */,
</span><ins>+                                7C882E0A1C80C764006BF731 /* UserContentWorld.mm in Sources */,
</ins><span class="cx">                                 7CCE7F271A411AF600447C4C /* UserContentController.mm in Sources */,
</span><span class="cx">                                 7CCE7F2D1A411B1000447C4C /* UserContentTest.mm in Sources */,
</span><span class="cx">                                 7CCE7F171A411AE600447C4C /* UserMedia.cpp in Sources */,
</span><span class="lines">@@ -1892,6 +1901,7 @@
</span><span class="cx">                         isa = PBXSourcesBuildPhase;
</span><span class="cx">                         buildActionMask = 2147483647;
</span><span class="cx">                         files = (
</span><ins>+                                7C882E091C80C630006BF731 /* UserContentWorldPlugIn.mm in Sources */,
</ins><span class="cx">                                 A13EBBAA1B87428D00097110 /* WebProcessPlugIn.mm in Sources */,
</span><span class="cx">                                 1A4F81CF1BDFFD53004E672E /* RemoteObjectRegistryPlugIn.mm in Sources */,
</span><span class="cx">                                 A13EBBB01B87436F00097110 /* BundleParametersPlugIn.mm in Sources */,
</span></span></pre></div>
<a id="trunkToolsTestWebKitAPITestsWebKit2CocoaUserContentWorldmm"></a>
<div class="addfile"><h4>Added: trunk/Tools/TestWebKitAPI/Tests/WebKit2Cocoa/UserContentWorld.mm (0 => 197172)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Tools/TestWebKitAPI/Tests/WebKit2Cocoa/UserContentWorld.mm                                (rev 0)
+++ trunk/Tools/TestWebKitAPI/Tests/WebKit2Cocoa/UserContentWorld.mm        2016-02-26 17:50:50 UTC (rev 197172)
</span><span class="lines">@@ -0,0 +1,178 @@
</span><ins>+/*
+ * Copyright (C) 2016 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import &quot;config.h&quot;
+#import &lt;WebKit/WKFoundation.h&gt;
+
+#if WK_API_ENABLED
+
+#import &quot;PlatformUtilities.h&quot;
+#import &quot;Test.h&quot;
+#import &quot;UserContentWorldProtocol.h&quot;
+#import &quot;WKWebViewConfigurationExtras.h&quot;
+#import &lt;WebKit/WKProcessPoolPrivate.h&gt;
+#import &lt;WebKit/WKUserContentControllerPrivate.h&gt;
+#import &lt;WebKit/WKUserScriptPrivate.h&gt;
+#import &lt;WebKit/WKWebViewPrivate.h&gt;
+#import &lt;WebKit/WebKit.h&gt;
+#import &lt;WebKit/_WKProcessPoolConfiguration.h&gt;
+#import &lt;WebKit/_WKRemoteObjectInterface.h&gt;
+#import &lt;WebKit/_WKRemoteObjectRegistry.h&gt;
+#import &lt;WebKit/_WKUserContentWorld.h&gt;
+#import &lt;WebKit/_WKUserStyleSheet.h&gt;
+#import &lt;wtf/RetainPtr.h&gt;
+
+static bool isDoneWithNavigation;
+
+@interface SimpleDelegate : NSObject &lt;WKNavigationDelegate&gt;
+@end
+
+@implementation SimpleDelegate
+- (void)webView:(WKWebView *)webView didFinishNavigation:(WKNavigation *)navigation
+{
+    isDoneWithNavigation = true;
+}
+@end
+
+
+TEST(UserContentWorld, NormalWorld)
+{
+    RetainPtr&lt;WKUserScript&gt; basicUserScript = adoptNS([[WKUserScript alloc] initWithSource:@&quot;&quot; injectionTime:WKUserScriptInjectionTimeAtDocumentStart forMainFrameOnly:YES]);
+    EXPECT_EQ([basicUserScript _userContentWorld], [_WKUserContentWorld normalWorld]);
+    EXPECT_NULL([basicUserScript _userContentWorld].name);
+}
+
+TEST(UserContentWorld, NormalWorldUserScript)
+{
+    RetainPtr&lt;WKWebViewConfiguration&gt; configuration = adoptNS([[WKWebViewConfiguration alloc] init]);
+
+    RetainPtr&lt;WKUserScript&gt; userScript = adoptNS([[WKUserScript alloc] initWithSource:@&quot;window.setFromUserScript = true;&quot; injectionTime:WKUserScriptInjectionTimeAtDocumentStart forMainFrameOnly:YES]);
+    [[configuration userContentController] addUserScript:userScript.get()];
+
+    RetainPtr&lt;WKWebView&gt; webView = adoptNS([[WKWebView alloc] initWithFrame:NSMakeRect(0, 0, 800, 600) configuration:configuration.get()]);
+
+    RetainPtr&lt;SimpleDelegate&gt; delegate = adoptNS([[SimpleDelegate alloc] init]);
+    [webView setNavigationDelegate:delegate.get()];
+
+    [webView loadHTMLString:@&quot;&lt;body style='background-color: red;'&gt;&lt;/body&gt;&quot; baseURL:nil];
+    TestWebKitAPI::Util::run(&amp;isDoneWithNavigation);
+    isDoneWithNavigation = false;
+
+    __block bool isDone = false;
+    [webView evaluateJavaScript:@&quot;window.setFromUserScript ? 'variable accessible' : 'variable inaccessible';&quot; completionHandler:^(id result, NSError *error) {
+        EXPECT_NULL(error);
+        EXPECT_TRUE([result isKindOfClass:[NSString class]]);
+        EXPECT_WK_STREQ(result, @&quot;variable accessible&quot;);
+
+        isDone = true;
+    }];
+
+    isDone = false;
+    TestWebKitAPI::Util::run(&amp;isDone);
+}
+
+TEST(UserContentWorld, IsolatedWorld)
+{
+    RetainPtr&lt;_WKUserContentWorld&gt; isolatedWorld = [_WKUserContentWorld worldWithName:@&quot;TestWorld&quot;];
+    EXPECT_WK_STREQ([isolatedWorld name], @&quot;TestWorld&quot;);
+
+    RetainPtr&lt;WKUserScript&gt; userScript = adoptNS([[WKUserScript alloc] _initWithSource:@&quot;&quot; injectionTime:WKUserScriptInjectionTimeAtDocumentStart forMainFrameOnly:YES legacyWhitelist:@[] legacyBlacklist:@[] userContentWorld:isolatedWorld.get()]);
+    EXPECT_EQ([userScript _userContentWorld], isolatedWorld.get());
+}
+
+TEST(UserContentWorld, IsolatedWorldUserScript)
+{
+    RetainPtr&lt;WKWebViewConfiguration&gt; configuration = adoptNS([[WKWebViewConfiguration alloc] init]);
+
+    RetainPtr&lt;_WKUserContentWorld&gt; isolatedWorld = [_WKUserContentWorld worldWithName:@&quot;TestWorld&quot;];
+    RetainPtr&lt;WKUserScript&gt; userScript = adoptNS([[WKUserScript alloc] _initWithSource:@&quot;window.setFromUserScript = true;&quot; injectionTime:WKUserScriptInjectionTimeAtDocumentStart forMainFrameOnly:YES legacyWhitelist:@[] legacyBlacklist:@[] userContentWorld:isolatedWorld.get()]);
+    [[configuration userContentController] addUserScript:userScript.get()];
+
+    RetainPtr&lt;WKWebView&gt; webView = adoptNS([[WKWebView alloc] initWithFrame:NSMakeRect(0, 0, 800, 600) configuration:configuration.get()]);
+
+    RetainPtr&lt;SimpleDelegate&gt; delegate = adoptNS([[SimpleDelegate alloc] init]);
+    [webView setNavigationDelegate:delegate.get()];
+
+    [webView loadHTMLString:@&quot;&lt;body style='background-color: red;'&gt;&lt;/body&gt;&quot; baseURL:nil];
+    TestWebKitAPI::Util::run(&amp;isDoneWithNavigation);
+    isDoneWithNavigation = false;
+
+    __block bool isDone = false;
+    [webView evaluateJavaScript:@&quot;window.setFromUserScript ? 'variable accessible' : 'variable inaccessible';&quot; completionHandler:^(id result, NSError *error) {
+        EXPECT_NULL(error);
+        EXPECT_TRUE([result isKindOfClass:[NSString class]]);
+        EXPECT_WK_STREQ(result, @&quot;variable inaccessible&quot;);
+
+        isDone = true;
+    }];
+
+    isDone = false;
+    TestWebKitAPI::Util::run(&amp;isDone);
+}
+
+static bool didObserveNormalWorld;
+static bool didObserveWorldWithName;
+
+@interface UserContentWorldRemoteObject : NSObject &lt;UserContentWorldProtocol&gt;
+@end
+
+@implementation UserContentWorldRemoteObject
+
+- (void)didObserveNormalWorld
+{
+    didObserveNormalWorld = true;
+}
+
+- (void)didObserveWorldWithName:(NSString *)name
+{
+    EXPECT_WK_STREQ(@&quot;TestWorld&quot;, name);
+    didObserveWorldWithName = true;
+}
+
+@end
+
+TEST(UserContentWorld, IsolatedWorldPlugIn)
+{
+    NSString * const testPlugInClassName = @&quot;UserContentWorldPlugIn&quot;;
+
+    RetainPtr&lt;WKWebViewConfiguration&gt; configuration = retainPtr([WKWebViewConfiguration testwebkitapi_configurationWithTestPlugInClassName:testPlugInClassName]);
+    
+    RetainPtr&lt;_WKUserContentWorld&gt; isolatedWorld = [_WKUserContentWorld worldWithName:@&quot;TestWorld&quot;];
+    RetainPtr&lt;WKUserScript&gt; userScript = adoptNS([[WKUserScript alloc] _initWithSource:@&quot;window.setFromUserScript = true;&quot; injectionTime:WKUserScriptInjectionTimeAtDocumentStart forMainFrameOnly:YES legacyWhitelist:@[] legacyBlacklist:@[] userContentWorld:isolatedWorld.get()]);
+    [[configuration userContentController] addUserScript:userScript.get()];
+
+    RetainPtr&lt;WKWebView&gt; webView = adoptNS([[WKWebView alloc] initWithFrame:NSMakeRect(0, 0, 800, 600) configuration:configuration.get()]);
+
+    RetainPtr&lt;UserContentWorldRemoteObject&gt; object = adoptNS([[UserContentWorldRemoteObject alloc] init]);
+    _WKRemoteObjectInterface *interface = [_WKRemoteObjectInterface remoteObjectInterfaceWithProtocol:@protocol(UserContentWorldProtocol)];
+    [[webView _remoteObjectRegistry] registerExportedObject:object.get() interface:interface];
+
+    [webView loadHTMLString:@&quot;&lt;body style='background-color: red;'&gt;&lt;/body&gt;&quot; baseURL:nil];
+
+    TestWebKitAPI::Util::run(&amp;didObserveNormalWorld);
+    TestWebKitAPI::Util::run(&amp;didObserveWorldWithName);
+}
+
+#endif
</ins></span></pre></div>
<a id="trunkToolsTestWebKitAPITestsWebKit2CocoaUserContentWorldPlugInmm"></a>
<div class="addfile"><h4>Added: trunk/Tools/TestWebKitAPI/Tests/WebKit2Cocoa/UserContentWorldPlugIn.mm (0 => 197172)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Tools/TestWebKitAPI/Tests/WebKit2Cocoa/UserContentWorldPlugIn.mm                                (rev 0)
+++ trunk/Tools/TestWebKitAPI/Tests/WebKit2Cocoa/UserContentWorldPlugIn.mm        2016-02-26 17:50:50 UTC (rev 197172)
</span><span class="lines">@@ -0,0 +1,77 @@
</span><ins>+/*
+ * Copyright (C) 2016 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import &quot;config.h&quot;
+
+#if WK_API_ENABLED
+
+#import &quot;PlatformUtilities.h&quot;
+#import &quot;UserContentWorldProtocol.h&quot;
+#import &lt;WebKit/WKConnection.h&gt;
+#import &lt;WebKit/WKWebProcessPlugIn.h&gt;
+#import &lt;WebKit/WKWebProcessPlugInBrowserContextController.h&gt;
+#import &lt;WebKit/WKWebProcessPlugInBrowserContextControllerPrivate.h&gt;
+#import &lt;WebKit/WKWebProcessPlugInFrame.h&gt;
+#import &lt;WebKit/WKWebProcessPlugInLoadDelegate.h&gt;
+#import &lt;WebKit/WKWebProcessPlugInScriptWorld.h&gt;
+#import &lt;WebKit/_WKRemoteObjectInterface.h&gt;
+#import &lt;WebKit/_WKRemoteObjectRegistry.h&gt;
+#import &lt;wtf/RetainPtr.h&gt;
+
+@interface UserContentWorldPlugIn : NSObject &lt;WKWebProcessPlugIn, WKWebProcessPlugInLoadDelegate&gt;
+@end
+
+@implementation UserContentWorldPlugIn {
+    RetainPtr&lt;WKWebProcessPlugInBrowserContextController&gt; _browserContextController;
+    RetainPtr&lt;WKWebProcessPlugInController&gt; _plugInController;
+    RetainPtr&lt;id &lt;UserContentWorldProtocol&gt;&gt; _remoteObject;
+}
+
+- (void)webProcessPlugIn:(WKWebProcessPlugInController *)plugInController didCreateBrowserContextController:(WKWebProcessPlugInBrowserContextController *)browserContextController
+{
+    ASSERT(!_browserContextController);
+    ASSERT(!_plugInController);
+    _browserContextController = browserContextController;
+    _plugInController = plugInController;
+
+    _WKRemoteObjectInterface *interface = [_WKRemoteObjectInterface remoteObjectInterfaceWithProtocol:@protocol(UserContentWorldProtocol)];
+    _remoteObject = [[browserContextController _remoteObjectRegistry] remoteObjectProxyWithInterface:interface];
+
+    [_browserContextController setLoadDelegate:self];
+}
+
+- (void)webProcessPlugInBrowserContextController:(WKWebProcessPlugInBrowserContextController*)controller globalObjectIsAvailableForFrame:(WKWebProcessPlugInFrame *)frame inScriptWorld:(WKWebProcessPlugInScriptWorld *)scriptWorld
+{
+    if (scriptWorld == [WKWebProcessPlugInScriptWorld normalWorld]) {
+        [_remoteObject didObserveNormalWorld];
+        return;
+    }
+
+    [_remoteObject didObserveWorldWithName:scriptWorld.name];
+}
+
+@end
+
+#endif // WK_API_ENABLED
</ins></span></pre></div>
<a id="trunkToolsTestWebKitAPITestsWebKit2CocoaUserContentWorldProtocolh"></a>
<div class="addfile"><h4>Added: trunk/Tools/TestWebKitAPI/Tests/WebKit2Cocoa/UserContentWorldProtocol.h (0 => 197172)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Tools/TestWebKitAPI/Tests/WebKit2Cocoa/UserContentWorldProtocol.h                                (rev 0)
+++ trunk/Tools/TestWebKitAPI/Tests/WebKit2Cocoa/UserContentWorldProtocol.h        2016-02-26 17:50:50 UTC (rev 197172)
</span><span class="lines">@@ -0,0 +1,37 @@
</span><ins>+/*
+ * Copyright (C) 2016 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import &lt;WebKit/WKFoundation.h&gt;
+
+#if WK_API_ENABLED
+
+@protocol UserContentWorldProtocol &lt;NSObject&gt;
+
+- (void)didObserveNormalWorld;
+- (void)didObserveWorldWithName:(NSString *)name;
+
+@end
+
+#endif
</ins></span></pre>
</div>
</div>

</body>
</html>