<!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>[181974] 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/181974">181974</a></dd>
<dt>Author</dt> <dd>weinig@apple.com</dd>
<dt>Date</dt> <dd>2015-03-25 15:38:58 -0700 (Wed, 25 Mar 2015)</dd>
</dl>

<h3>Log Message</h3>
<pre>[Content Extensions] Convert content extension compiling to return error codes and write its output using a client
https://bugs.webkit.org/show_bug.cgi?id=143059

Reviewed by Alex Christensen.

Source/WebCore:

* WebCore.xcodeproj/project.pbxproj:
Add ContentExtensionError.h/cpp.

* contentextensions/ContentExtensionError.cpp: Added.
(WebCore::ContentExtensions::contentExtensionErrorCategory):
* contentextensions/ContentExtensionError.h: Added.
(WebCore::ContentExtensions::make_error_code):
Add ContentExtensionError enum and std::error_code adaptor.

* contentextensions/ContentExtensionCompiler.h:
Instead of returning CompiledContentExtensionData, use a client interface
to pass data. Eventually, this should be turned into a direct streaming 
interface so we can write directly to a file.

* contentextensions/ContentExtensionCompiler.cpp:
(WebCore::ContentExtensions::compileRuleList):
* contentextensions/ContentExtensionParser.cpp:
(WebCore::ContentExtensions::getTypeFlags):
(WebCore::ContentExtensions::loadTrigger):
(WebCore::ContentExtensions::loadAction):
(WebCore::ContentExtensions::loadRule):
(WebCore::ContentExtensions::loadEncodedRules):
(WebCore::ContentExtensions::parseRuleList):
* contentextensions/ContentExtensionParser.h:
Convert to return an error.

Source/WebKit2:

* Shared/WebCompiledContentExtension.cpp:
* Shared/WebCompiledContentExtension.h:
(WebKit::LegacyContentExtensionCompilationClient::LegacyContentExtensionCompilationClient):
(WebKit::LegacyContentExtensionCompilationClient::writeBytecode):
(WebKit::LegacyContentExtensionCompilationClient::writeActions):
Add subclass of ContentExtensionCompilationClient for use with the non-file backed content
extensions.

* UIProcess/API/C/WKUserContentFilterRef.cpp:
(WKUserContentFilterCreate):
* UIProcess/API/Cocoa/_WKUserContentFilter.mm:
(-[_WKUserContentFilter initWithName:serializedRules:]):
Update to use the new interface of compileRuleList().

Tools:

* TestWebKitAPI/Tests/WebCore/ContentExtensions.cpp:
(TestWebKitAPI::InMemoryCompiledContentExtension::createFromFilter):
Update for new interface of compileRuleList().</pre>

<h3>Modified Paths</h3>
<ul>
<li><a href="#trunkSourceWebCoreChangeLog">trunk/Source/WebCore/ChangeLog</a></li>
<li><a href="#trunkSourceWebCoreWebCorexcodeprojprojectpbxproj">trunk/Source/WebCore/WebCore.xcodeproj/project.pbxproj</a></li>
<li><a href="#trunkSourceWebCorecontentextensionsContentExtensionCompilercpp">trunk/Source/WebCore/contentextensions/ContentExtensionCompiler.cpp</a></li>
<li><a href="#trunkSourceWebCorecontentextensionsContentExtensionCompilerh">trunk/Source/WebCore/contentextensions/ContentExtensionCompiler.h</a></li>
<li><a href="#trunkSourceWebCorecontentextensionsContentExtensionParsercpp">trunk/Source/WebCore/contentextensions/ContentExtensionParser.cpp</a></li>
<li><a href="#trunkSourceWebCorecontentextensionsContentExtensionParserh">trunk/Source/WebCore/contentextensions/ContentExtensionParser.h</a></li>
<li><a href="#trunkSourceWebKit2ChangeLog">trunk/Source/WebKit2/ChangeLog</a></li>
<li><a href="#trunkSourceWebKit2SharedWebCompiledContentExtensioncpp">trunk/Source/WebKit2/Shared/WebCompiledContentExtension.cpp</a></li>
<li><a href="#trunkSourceWebKit2SharedWebCompiledContentExtensionh">trunk/Source/WebKit2/Shared/WebCompiledContentExtension.h</a></li>
<li><a href="#trunkSourceWebKit2UIProcessAPICWKUserContentFilterRefcpp">trunk/Source/WebKit2/UIProcess/API/C/WKUserContentFilterRef.cpp</a></li>
<li><a href="#trunkSourceWebKit2UIProcessAPICocoa_WKUserContentFiltermm">trunk/Source/WebKit2/UIProcess/API/Cocoa/_WKUserContentFilter.mm</a></li>
<li><a href="#trunkToolsChangeLog">trunk/Tools/ChangeLog</a></li>
<li><a href="#trunkToolsTestWebKitAPITestsWebCoreContentExtensionscpp">trunk/Tools/TestWebKitAPI/Tests/WebCore/ContentExtensions.cpp</a></li>
</ul>

<h3>Added Paths</h3>
<ul>
<li><a href="#trunkSourceWebCorecontentextensionsContentExtensionErrorcpp">trunk/Source/WebCore/contentextensions/ContentExtensionError.cpp</a></li>
<li><a href="#trunkSourceWebCorecontentextensionsContentExtensionErrorh">trunk/Source/WebCore/contentextensions/ContentExtensionError.h</a></li>
</ul>

</div>
<div id="patch">
<h3>Diff</h3>
<a id="trunkSourceWebCoreChangeLog"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/ChangeLog (181973 => 181974)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/ChangeLog        2015-03-25 21:33:59 UTC (rev 181973)
+++ trunk/Source/WebCore/ChangeLog        2015-03-25 22:38:58 UTC (rev 181974)
</span><span class="lines">@@ -1,3 +1,36 @@
</span><ins>+2015-03-25  Sam Weinig  &lt;sam@webkit.org&gt;
+
+        [Content Extensions] Convert content extension compiling to return error codes and write its output using a client
+        https://bugs.webkit.org/show_bug.cgi?id=143059
+
+        Reviewed by Alex Christensen.
+
+        * WebCore.xcodeproj/project.pbxproj:
+        Add ContentExtensionError.h/cpp.
+
+        * contentextensions/ContentExtensionError.cpp: Added.
+        (WebCore::ContentExtensions::contentExtensionErrorCategory):
+        * contentextensions/ContentExtensionError.h: Added.
+        (WebCore::ContentExtensions::make_error_code):
+        Add ContentExtensionError enum and std::error_code adaptor.
+
+        * contentextensions/ContentExtensionCompiler.h:
+        Instead of returning CompiledContentExtensionData, use a client interface
+        to pass data. Eventually, this should be turned into a direct streaming 
+        interface so we can write directly to a file.
+
+        * contentextensions/ContentExtensionCompiler.cpp:
+        (WebCore::ContentExtensions::compileRuleList):
+        * contentextensions/ContentExtensionParser.cpp:
+        (WebCore::ContentExtensions::getTypeFlags):
+        (WebCore::ContentExtensions::loadTrigger):
+        (WebCore::ContentExtensions::loadAction):
+        (WebCore::ContentExtensions::loadRule):
+        (WebCore::ContentExtensions::loadEncodedRules):
+        (WebCore::ContentExtensions::parseRuleList):
+        * contentextensions/ContentExtensionParser.h:
+        Convert to return an error.
+
</ins><span class="cx"> 2015-03-25  Beth Dakin  &lt;bdakin@apple.com&gt;
</span><span class="cx"> 
</span><span class="cx">         REGRESSION (r181660): Safari navigates to link after a starting and canceling a 
</span></span></pre></div>
<a id="trunkSourceWebCoreWebCorexcodeprojprojectpbxproj"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/WebCore.xcodeproj/project.pbxproj (181973 => 181974)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/WebCore.xcodeproj/project.pbxproj        2015-03-25 21:33:59 UTC (rev 181973)
+++ trunk/Source/WebCore/WebCore.xcodeproj/project.pbxproj        2015-03-25 22:38:58 UTC (rev 181974)
</span><span class="lines">@@ -2539,6 +2539,8 @@
</span><span class="cx">                 7CE683471921821500F4D928 /* UserMessageHandlerDescriptorTypes.h in Headers */ = {isa = PBXBuildFile; fileRef = 7CE683461921821500F4D928 /* UserMessageHandlerDescriptorTypes.h */; settings = {ATTRIBUTES = (Private, ); }; };
</span><span class="cx">                 7CE6CBFB187F370700D46BF5 /* FormatConverter.h in Headers */ = {isa = PBXBuildFile; fileRef = 7CE6CBFA187F370700D46BF5 /* FormatConverter.h */; };
</span><span class="cx">                 7CE6CBFD187F394900D46BF5 /* FormatConverter.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 7CE6CBFC187F394900D46BF5 /* FormatConverter.cpp */; };
</span><ins>+                7CFDC57C1AC1D80500E24A57 /* ContentExtensionError.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 7CFDC57A1AC1D80500E24A57 /* ContentExtensionError.cpp */; };
+                7CFDC57D1AC1D80500E24A57 /* ContentExtensionError.h in Headers */ = {isa = PBXBuildFile; fileRef = 7CFDC57B1AC1D80500E24A57 /* ContentExtensionError.h */; settings = {ATTRIBUTES = (Private, ); }; };
</ins><span class="cx">                 7D741BDA177226AA00859170 /* CSSValueKeywords.h in Copy Generated Headers */ = {isa = PBXBuildFile; fileRef = 6565814809D13043000E61D7 /* CSSValueKeywords.h */; };
</span><span class="cx">                 7E37EF2E1339208800B29250 /* SubresourceLoaderCF.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 7E37EF2D1339208800B29250 /* SubresourceLoaderCF.cpp */; };
</span><span class="cx">                 7E428CE513E3407F003B661C /* ResourceHandleIOS.mm in Sources */ = {isa = PBXBuildFile; fileRef = 7E428CE413E3407F003B661C /* ResourceHandleIOS.mm */; };
</span><span class="lines">@@ -9788,6 +9790,8 @@
</span><span class="cx">                 7CE683461921821500F4D928 /* UserMessageHandlerDescriptorTypes.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = UserMessageHandlerDescriptorTypes.h; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="cx">                 7CE6CBFA187F370700D46BF5 /* FormatConverter.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = FormatConverter.h; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="cx">                 7CE6CBFC187F394900D46BF5 /* FormatConverter.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = FormatConverter.cpp; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><ins>+                7CFDC57A1AC1D80500E24A57 /* ContentExtensionError.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = ContentExtensionError.cpp; sourceTree = &quot;&lt;group&gt;&quot;; };
+                7CFDC57B1AC1D80500E24A57 /* ContentExtensionError.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = ContentExtensionError.h; sourceTree = &quot;&lt;group&gt;&quot;; };
</ins><span class="cx">                 7E37EF2D1339208800B29250 /* SubresourceLoaderCF.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; name = SubresourceLoaderCF.cpp; path = cf/SubresourceLoaderCF.cpp; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="cx">                 7E428CE413E3407F003B661C /* ResourceHandleIOS.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = ResourceHandleIOS.mm; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="cx">                 7E46F6F81627A2C900062223 /* JSOESElementIndexUint.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = JSOESElementIndexUint.cpp; sourceTree = &quot;&lt;group&gt;&quot;; };
</span><span class="lines">@@ -15501,6 +15505,8 @@
</span><span class="cx">                                 7C93F3471AA6BA5E00A98BAB /* CompiledContentExtension.cpp */,
</span><span class="cx">                                 7C93F3481AA6BA5E00A98BAB /* CompiledContentExtension.h */,
</span><span class="cx">                                 5CDFA6C71AA4F2DA00EA8746 /* ContentExtensionActions.h */,
</span><ins>+                                7CFDC57A1AC1D80500E24A57 /* ContentExtensionError.cpp */,
+                                7CFDC57B1AC1D80500E24A57 /* ContentExtensionError.h */,
</ins><span class="cx">                                 7C93F34B1AA6BF0700A98BAB /* ContentExtensionCompiler.cpp */,
</span><span class="cx">                                 7C93F34C1AA6BF0700A98BAB /* ContentExtensionCompiler.h */,
</span><span class="cx">                                 26F0C8951A2E724B002794F8 /* ContentExtensionParser.cpp */,
</span><span class="lines">@@ -25413,6 +25419,7 @@
</span><span class="cx">                                 B2FA3D9B0AB75A6F000E5AC4 /* JSSVGGElement.h in Headers */,
</span><span class="cx">                                 724ED3321A3A8B2300F5F13C /* JSEXTBlendMinMax.h in Headers */,
</span><span class="cx">                                 B27B28280CEF0C0700D39D54 /* JSSVGGlyphElement.h in Headers */,
</span><ins>+                                7CFDC57D1AC1D80500E24A57 /* ContentExtensionError.h in Headers */,
</ins><span class="cx">                                 24D9129A13CA971400D21915 /* JSSVGGlyphRefElement.h in Headers */,
</span><span class="cx">                                 B2FA3D9D0AB75A6F000E5AC4 /* JSSVGGradientElement.h in Headers */,
</span><span class="cx">                                 7BE7427381FA906FBB4F0F2C /* JSSVGGraphicsElement.h in Headers */,
</span><span class="lines">@@ -28429,6 +28436,7 @@
</span><span class="cx">                                 F350B73513F1377D00880C43 /* InstrumentingAgents.cpp in Sources */,
</span><span class="cx">                                 2D46F04E17B96FBD005647F0 /* IntPoint.cpp in Sources */,
</span><span class="cx">                                 B27535600B053814002CE64F /* IntPointCG.cpp in Sources */,
</span><ins>+                                7CFDC57C1AC1D80500E24A57 /* ContentExtensionError.cpp in Sources */,
</ins><span class="cx">                                 B275357C0B053814002CE64F /* IntPointMac.mm in Sources */,
</span><span class="cx">                                 B27535730B053814002CE64F /* IntRect.cpp in Sources */,
</span><span class="cx">                                 B27535610B053814002CE64F /* IntRectCG.cpp in Sources */,
</span></span></pre></div>
<a id="trunkSourceWebCorecontentextensionsContentExtensionCompilercpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/contentextensions/ContentExtensionCompiler.cpp (181973 => 181974)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/contentextensions/ContentExtensionCompiler.cpp        2015-03-25 21:33:59 UTC (rev 181973)
+++ trunk/Source/WebCore/contentextensions/ContentExtensionCompiler.cpp        2015-03-25 22:38:58 UTC (rev 181974)
</span><span class="lines">@@ -30,6 +30,7 @@
</span><span class="cx"> 
</span><span class="cx"> #include &quot;CompiledContentExtension.h&quot;
</span><span class="cx"> #include &quot;ContentExtensionActions.h&quot;
</span><ins>+#include &quot;ContentExtensionError.h&quot;
</ins><span class="cx"> #include &quot;ContentExtensionParser.h&quot;
</span><span class="cx"> #include &quot;ContentExtensionRule.h&quot;
</span><span class="cx"> #include &quot;ContentExtensionsDebugging.h&quot;
</span><span class="lines">@@ -99,9 +100,12 @@
</span><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> 
</span><del>-CompiledContentExtensionData compileRuleList(const String&amp; ruleList)
</del><ins>+std::error_code compileRuleList(const String&amp; ruleList, ContentExtensionCompilationClient&amp; client)
</ins><span class="cx"> {
</span><del>-    auto parsedRuleList = parseRuleList(ruleList);
</del><ins>+    Vector&lt;ContentExtensionRule&gt; parsedRuleList;
+    auto parserError = parseRuleList(ruleList, parsedRuleList);
+    if (parserError)
+        return parserError;
</ins><span class="cx"> 
</span><span class="cx"> #if CONTENT_EXTENSIONS_PERFORMANCE_REPORTING
</span><span class="cx">     double nfaBuildTimeStart = monotonicallyIncreasingTime();
</span><span class="lines">@@ -178,7 +182,10 @@
</span><span class="cx">     dfa.debugPrintDot();
</span><span class="cx"> #endif
</span><span class="cx"> 
</span><del>-    return { WTF::move(bytecode), WTF::move(actions) };
</del><ins>+    client.writeBytecode(WTF::move(bytecode));
+    client.writeActions(WTF::move(actions));
+
+    return { };
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> } // namespace ContentExtensions
</span></span></pre></div>
<a id="trunkSourceWebCorecontentextensionsContentExtensionCompilerh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/contentextensions/ContentExtensionCompiler.h (181973 => 181974)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/contentextensions/ContentExtensionCompiler.h        2015-03-25 21:33:59 UTC (rev 181973)
+++ trunk/Source/WebCore/contentextensions/ContentExtensionCompiler.h        2015-03-25 22:38:58 UTC (rev 181974)
</span><span class="lines">@@ -29,6 +29,7 @@
</span><span class="cx"> #if ENABLE(CONTENT_EXTENSIONS)
</span><span class="cx"> 
</span><span class="cx"> #include &quot;CompiledContentExtension.h&quot;
</span><ins>+#include &lt;system_error&gt;
</ins><span class="cx"> #include &lt;wtf/Forward.h&gt;
</span><span class="cx"> #include &lt;wtf/Ref.h&gt;
</span><span class="cx"> 
</span><span class="lines">@@ -40,8 +41,16 @@
</span><span class="cx">     Vector&lt;SerializedActionByte&gt; actions;
</span><span class="cx"> };
</span><span class="cx"> 
</span><del>-WEBCORE_EXPORT CompiledContentExtensionData compileRuleList(const String&amp;);
</del><ins>+class ContentExtensionCompilationClient {
+public:
+    virtual ~ContentExtensionCompilationClient() { }
+    
+    virtual void writeBytecode(Vector&lt;DFABytecode&gt;&amp;&amp;) = 0;
+    virtual void writeActions(Vector&lt;SerializedActionByte&gt;&amp;&amp;) = 0;
+};
</ins><span class="cx"> 
</span><ins>+WEBCORE_EXPORT std::error_code compileRuleList(const String&amp;, ContentExtensionCompilationClient&amp;);
+
</ins><span class="cx"> } // namespace ContentExtensions
</span><span class="cx"> } // namespace WebCore
</span><span class="cx"> 
</span></span></pre></div>
<a id="trunkSourceWebCorecontentextensionsContentExtensionErrorcpp"></a>
<div class="addfile"><h4>Added: trunk/Source/WebCore/contentextensions/ContentExtensionError.cpp (0 => 181974)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/contentextensions/ContentExtensionError.cpp                                (rev 0)
+++ trunk/Source/WebCore/contentextensions/ContentExtensionError.cpp        2015-03-25 22:38:58 UTC (rev 181974)
</span><span class="lines">@@ -0,0 +1,89 @@
</span><ins>+/*
+ * Copyright (C) 2015 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;ContentExtensionError.h&quot;
+
+#if ENABLE(CONTENT_EXTENSIONS)
+
+#include &lt;string&gt;
+#include &lt;wtf/NeverDestroyed.h&gt;
+
+namespace WebCore {
+namespace ContentExtensions {
+
+const std::error_category&amp; contentExtensionErrorCategory()
+{
+    class ContentExtensionErrorCategory : public std::error_category {
+        const char* name() const noexcept override
+        {
+            return &quot;content extension&quot;;
+        }
+
+        virtual std::string message(int errorCode) const override
+        {
+            switch (static_cast&lt;ContentExtensionError&gt;(errorCode)) {
+            case ContentExtensionError::JSONInvalid:
+                return &quot;Failed to parse the JSON String.&quot;;
+            case ContentExtensionError::JSONTopLevelStructureNotAnObject:
+                return &quot;Invalid input, the top level structure is not an object.&quot;;
+            case ContentExtensionError::JSONTopLevelStructureNotAnArray:
+                return &quot;Invalid input, the top level structure is not an array.&quot;;
+            case ContentExtensionError::JSONInvalidObjectInTopLevelArray:
+                return &quot;Invalid object in the top level array.&quot;;
+            case ContentExtensionError::JSONInvalidRule:
+                return &quot;Invalid rule.&quot;;
+            case ContentExtensionError::JSONContainsNoRules:
+                return &quot;Empty extension.&quot;;
+            case ContentExtensionError::JSONInvalidTrigger:
+                return &quot;Invalid trigger object.&quot;;
+            case ContentExtensionError::JSONInvalidURLFilterInTrigger:
+                return &quot;Invalid url-filter object.&quot;;
+            case ContentExtensionError::JSONInvalidTriggerFlagsArray:
+                return &quot;Invalid trigger flags array.&quot;;
+            case ContentExtensionError::JSONInvalidObjectInTriggerFlagsArray:
+                return &quot;Invalid object in the trigger flags array.&quot;;
+            case ContentExtensionError::JSONInvalidStringInTriggerFlagsArray:
+                return &quot;Invalid string in the trigger flags array.&quot;;
+            case ContentExtensionError::JSONInvalidAction:
+                return &quot;Invalid action object.&quot;;
+            case ContentExtensionError::JSONInvalidActionType:
+                return &quot;Invalid action type.&quot;;
+            case ContentExtensionError::JSONInvalidCSSDisplayNoneActionType:
+                return &quot;Invalid css-display-none action type. Requires a selector.&quot;;
+            }
+
+            return std::string();
+        }
+    };
+
+    static NeverDestroyed&lt;ContentExtensionErrorCategory&gt; contentExtensionErrorCategory;
+    return contentExtensionErrorCategory;
+}
+
+} // namespace ContentExtensions
+} // namespace WebCore
+
+#endif // ENABLE(CONTENT_EXTENSIONS)
</ins></span></pre></div>
<a id="trunkSourceWebCorecontentextensionsContentExtensionErrorh"></a>
<div class="addfile"><h4>Added: trunk/Source/WebCore/contentextensions/ContentExtensionError.h (0 => 181974)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/contentextensions/ContentExtensionError.h                                (rev 0)
+++ trunk/Source/WebCore/contentextensions/ContentExtensionError.h        2015-03-25 22:38:58 UTC (rev 181974)
</span><span class="lines">@@ -0,0 +1,73 @@
</span><ins>+/*
+ * Copyright (C) 2015 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 ContentExtensionError_h
+#define ContentExtensionError_h
+
+#if ENABLE(CONTENT_EXTENSIONS)
+
+#include &lt;system_error&gt;
+
+namespace WebCore {
+namespace ContentExtensions {
+
+enum class ContentExtensionError {
+    // JSON parser error
+    JSONInvalid = 1,
+    
+    // JSON semantics error
+    JSONTopLevelStructureNotAnObject,
+    JSONTopLevelStructureNotAnArray,
+    JSONInvalidObjectInTopLevelArray,
+    JSONInvalidRule,
+    JSONContainsNoRules,
+    
+    JSONInvalidTrigger,
+    JSONInvalidURLFilterInTrigger,
+    JSONInvalidTriggerFlagsArray,
+    JSONInvalidObjectInTriggerFlagsArray,
+    JSONInvalidStringInTriggerFlagsArray,
+    
+    JSONInvalidAction,
+    JSONInvalidActionType,
+    JSONInvalidCSSDisplayNoneActionType,
+};
+
+const std::error_category&amp; contentExtensionErrorCategory();
+
+inline std::error_code make_error_code(ContentExtensionError error)
+{
+    return { static_cast&lt;int&gt;(error), contentExtensionErrorCategory() };
+}
+
+} // namespace ContentExtensions
+} // namespace WebCore
+
+namespace std {
+    template&lt;&gt; struct is_error_code_enum&lt;WebCore::ContentExtensions::ContentExtensionError&gt; : public true_type { };
+}
+
+#endif // ENABLE(CONTENT_EXTENSIONS)
+#endif // ContentExtensionError_h
</ins></span></pre></div>
<a id="trunkSourceWebCorecontentextensionsContentExtensionParsercpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/contentextensions/ContentExtensionParser.cpp (181973 => 181974)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/contentextensions/ContentExtensionParser.cpp        2015-03-25 21:33:59 UTC (rev 181973)
+++ trunk/Source/WebCore/contentextensions/ContentExtensionParser.cpp        2015-03-25 22:38:58 UTC (rev 181974)
</span><span class="lines">@@ -28,6 +28,7 @@
</span><span class="cx"> 
</span><span class="cx"> #if ENABLE(CONTENT_EXTENSIONS)
</span><span class="cx"> 
</span><ins>+#include &quot;ContentExtensionError.h&quot;
</ins><span class="cx"> #include &quot;ContentExtensionRule.h&quot;
</span><span class="cx"> #include &quot;ContentExtensionsBackend.h&quot;
</span><span class="cx"> #include &quot;ContentExtensionsDebugging.h&quot;
</span><span class="lines">@@ -46,57 +47,48 @@
</span><span class="cx"> 
</span><span class="cx"> namespace ContentExtensions {
</span><span class="cx"> 
</span><del>-static bool getTypeFlags(ExecState&amp; exec, const JSValue&amp; typeValue, ResourceFlags&amp; flags, uint16_t(*stringToType)(const String&amp;))
</del><ins>+static std::error_code getTypeFlags(ExecState&amp; exec, const JSValue&amp; typeValue, ResourceFlags&amp; flags, uint16_t(*stringToType)(const String&amp;))
</ins><span class="cx"> {
</span><span class="cx">     if (!typeValue.isObject())
</span><del>-        return true;
</del><ins>+        return { };
</ins><span class="cx"> 
</span><span class="cx">     JSObject* object = typeValue.toObject(&amp;exec);
</span><del>-    if (!isJSArray(object)) {
-        WTFLogAlways(&quot;Invalid trigger flags array&quot;);
-        return false;
-    }
</del><ins>+    if (!isJSArray(object))
+        return ContentExtensionError::JSONInvalidTriggerFlagsArray;
</ins><span class="cx"> 
</span><span class="cx">     JSArray* array = jsCast&lt;JSArray*&gt;(object);
</span><span class="cx">     
</span><span class="cx">     unsigned length = array-&gt;length();
</span><span class="cx">     for (unsigned i = 0; i &lt; length; ++i) {
</span><span class="cx">         JSValue value = array-&gt;getIndex(&amp;exec, i);
</span><del>-        if (exec.hadException() || !value) {
-            WTFLogAlways(&quot;Invalid object in the trigger flags array.&quot;);
-            continue;
-        }
</del><ins>+        if (exec.hadException() || !value)
+            return ContentExtensionError::JSONInvalidObjectInTriggerFlagsArray;
</ins><span class="cx">         
</span><span class="cx">         String name = value.toWTFString(&amp;exec);
</span><span class="cx">         uint16_t type = stringToType(name);
</span><del>-        if (!type) {
-            WTFLogAlways(&quot;Invalid string in the trigger flags array.&quot;);
-            continue;
-        }
</del><ins>+        if (!type)
+            return ContentExtensionError::JSONInvalidStringInTriggerFlagsArray;
+
</ins><span class="cx">         flags |= type;
</span><span class="cx">     }
</span><del>-    return true;
</del><ins>+
+    return { };
</ins><span class="cx"> }
</span><span class="cx">     
</span><del>-static bool loadTrigger(ExecState&amp; exec, JSObject&amp; ruleObject, Trigger&amp; trigger)
</del><ins>+static std::error_code loadTrigger(ExecState&amp; exec, JSObject&amp; ruleObject, Trigger&amp; trigger)
</ins><span class="cx"> {
</span><span class="cx">     JSValue triggerObject = ruleObject.get(&amp;exec, Identifier(&amp;exec, &quot;trigger&quot;));
</span><del>-    if (!triggerObject || exec.hadException() || !triggerObject.isObject()) {
-        WTFLogAlways(&quot;Invalid trigger object.&quot;);
-        return false;
-    }
-
</del><ins>+    if (!triggerObject || exec.hadException() || !triggerObject.isObject())
+        return ContentExtensionError::JSONInvalidTrigger;
+    
</ins><span class="cx">     JSValue urlFilterObject = triggerObject.get(&amp;exec, Identifier(&amp;exec, &quot;url-filter&quot;));
</span><del>-    if (!urlFilterObject || exec.hadException() || !urlFilterObject.isString()) {
-        WTFLogAlways(&quot;Invalid url-filter object.&quot;);
-        return false;
-    }
</del><ins>+    if (!urlFilterObject || exec.hadException() || !urlFilterObject.isString())
+        return ContentExtensionError::JSONInvalidURLFilterInTrigger;
</ins><span class="cx"> 
</span><span class="cx">     String urlFilter = urlFilterObject.toWTFString(&amp;exec);
</span><del>-    if (urlFilter.isEmpty()) {
-        WTFLogAlways(&quot;Invalid url-filter object. The url is empty.&quot;);
-        return false;
-    }
</del><ins>+    if (urlFilter.isEmpty())
+        return ContentExtensionError::JSONInvalidURLFilterInTrigger;
+
</ins><span class="cx">     trigger.urlFilter = urlFilter;
</span><span class="cx"> 
</span><span class="cx">     JSValue urlFilterCaseValue = triggerObject.get(&amp;exec, Identifier(&amp;exec, &quot;url-filter-is-case-sensitive&quot;));
</span><span class="lines">@@ -104,29 +96,31 @@
</span><span class="cx">         trigger.urlFilterIsCaseSensitive = urlFilterCaseValue.toBoolean(&amp;exec);
</span><span class="cx"> 
</span><span class="cx">     JSValue resourceTypeValue = triggerObject.get(&amp;exec, Identifier(&amp;exec, &quot;resource-type&quot;));
</span><del>-    if (resourceTypeValue &amp;&amp; !exec.hadException() &amp;&amp; !getTypeFlags(exec, resourceTypeValue, trigger.flags, readResourceType))
-        return false;
-    
</del><ins>+    if (resourceTypeValue &amp;&amp; !exec.hadException()) {
+        auto typeFlagsError = getTypeFlags(exec, resourceTypeValue, trigger.flags, readResourceType);
+        if (typeFlagsError)
+            return typeFlagsError;
+    }
+
</ins><span class="cx">     JSValue loadTypeValue = triggerObject.get(&amp;exec, Identifier(&amp;exec, &quot;load-type&quot;));
</span><del>-    if (loadTypeValue &amp;&amp; !exec.hadException() &amp;&amp; !getTypeFlags(exec, loadTypeValue, trigger.flags, readLoadType))
-        return false;
</del><ins>+    if (loadTypeValue &amp;&amp; !exec.hadException()) {
+        auto typeFlagsError = getTypeFlags(exec, loadTypeValue, trigger.flags, readLoadType);
+        if (typeFlagsError)
+            return typeFlagsError;
+    }
</ins><span class="cx"> 
</span><del>-    return true;
</del><ins>+    return { };
</ins><span class="cx"> }
</span><span class="cx"> 
</span><del>-static bool loadAction(ExecState&amp; exec, JSObject&amp; ruleObject, Action&amp; action)
</del><ins>+static std::error_code loadAction(ExecState&amp; exec, JSObject&amp; ruleObject, Action&amp; action)
</ins><span class="cx"> {
</span><span class="cx">     JSValue actionObject = ruleObject.get(&amp;exec, Identifier(&amp;exec, &quot;action&quot;));
</span><del>-    if (!actionObject || exec.hadException() || !actionObject.isObject()) {
-        WTFLogAlways(&quot;Invalid action object.&quot;);
-        return false;
-    }
</del><ins>+    if (!actionObject || exec.hadException() || !actionObject.isObject())
+        return ContentExtensionError::JSONInvalidAction;
</ins><span class="cx"> 
</span><span class="cx">     JSValue typeObject = actionObject.get(&amp;exec, Identifier(&amp;exec, &quot;type&quot;));
</span><del>-    if (!typeObject || exec.hadException() || !typeObject.isString()) {
-        WTFLogAlways(&quot;Invalid url-filter object.&quot;);
-        return false;
-    }
</del><ins>+    if (!typeObject || exec.hadException() || !typeObject.isString())
+        return ContentExtensionError::JSONInvalidActionType;
</ins><span class="cx"> 
</span><span class="cx">     String actionType = typeObject.toWTFString(&amp;exec);
</span><span class="cx"> 
</span><span class="lines">@@ -138,77 +132,73 @@
</span><span class="cx">         action = ActionType::BlockCookies;
</span><span class="cx">     else if (actionType == &quot;css-display-none&quot;) {
</span><span class="cx">         JSValue selector = actionObject.get(&amp;exec, Identifier(&amp;exec, &quot;selector&quot;));
</span><del>-        if (!selector || exec.hadException() || !selector.isString()) {
-            WTFLogAlways(&quot;css-display-none action type requires a selector&quot;);
-            return false;
-        }
</del><ins>+        if (!selector || exec.hadException() || !selector.isString())
+            return ContentExtensionError::JSONInvalidCSSDisplayNoneActionType;
+
</ins><span class="cx">         action = Action(ActionType::CSSDisplayNoneSelector, selector.toWTFString(&amp;exec));
</span><del>-    } else {
-        WTFLogAlways(&quot;Unrecognized action: \&quot;%s\&quot;&quot;, actionType.utf8().data());
-        return false;
-    }
</del><ins>+    } else
+        return ContentExtensionError::JSONInvalidActionType;
</ins><span class="cx"> 
</span><del>-    return true;
</del><ins>+    return { };
</ins><span class="cx"> }
</span><span class="cx"> 
</span><del>-static void loadRule(ExecState&amp; exec, JSObject&amp; ruleObject, Vector&lt;ContentExtensionRule&gt;&amp; ruleList)
</del><ins>+static std::error_code loadRule(ExecState&amp; exec, JSObject&amp; ruleObject, Vector&lt;ContentExtensionRule&gt;&amp; ruleList)
</ins><span class="cx"> {
</span><span class="cx">     Trigger trigger;
</span><del>-    if (!loadTrigger(exec, ruleObject, trigger))
-        return;
</del><ins>+    auto triggerError = loadTrigger(exec, ruleObject, trigger);
+    if (triggerError)
+        return triggerError;
</ins><span class="cx"> 
</span><span class="cx">     Action action;
</span><del>-    if (!loadAction(exec, ruleObject, action))
-        return;
</del><ins>+    auto actionError = loadAction(exec, ruleObject, action);
+    if (actionError)
+        return actionError;
</ins><span class="cx"> 
</span><span class="cx">     ruleList.append(ContentExtensionRule(trigger, action));
</span><ins>+    return { };
</ins><span class="cx"> }
</span><span class="cx"> 
</span><del>-static Vector&lt;ContentExtensionRule&gt; loadEncodedRules(ExecState&amp; exec, const String&amp; rules)
</del><ins>+static std::error_code loadEncodedRules(ExecState&amp; exec, const String&amp; rules, Vector&lt;ContentExtensionRule&gt;&amp; ruleList)
</ins><span class="cx"> {
</span><span class="cx">     JSValue decodedRules = JSONParse(&amp;exec, rules);
</span><span class="cx"> 
</span><del>-    if (exec.hadException() || !decodedRules) {
-        WTFLogAlways(&quot;Failed to parse the JSON string.&quot;);
-        return Vector&lt;ContentExtensionRule&gt;();
-    }
</del><ins>+    if (exec.hadException() || !decodedRules)
+        return ContentExtensionError::JSONInvalid;
</ins><span class="cx"> 
</span><del>-    if (decodedRules.isObject()) {
-        JSObject* topLevelObject = decodedRules.toObject(&amp;exec);
-        if (!topLevelObject || exec.hadException()) {
-            WTFLogAlways(&quot;Invalid input, the top level structure is not an object.&quot;);
-            return Vector&lt;ContentExtensionRule&gt;();
-        }
</del><ins>+    if (!decodedRules.isObject())
+        return ContentExtensionError::JSONTopLevelStructureNotAnObject;
</ins><span class="cx"> 
</span><del>-        if (!isJSArray(topLevelObject)) {
-            WTFLogAlways(&quot;Invalid input, the top level object is not an array.&quot;);
-            return Vector&lt;ContentExtensionRule&gt;();
-        }
</del><ins>+    JSObject* topLevelObject = decodedRules.toObject(&amp;exec);
+    if (!topLevelObject || exec.hadException())
+        return ContentExtensionError::JSONTopLevelStructureNotAnObject;
+    
+    if (!isJSArray(topLevelObject))
+        return ContentExtensionError::JSONTopLevelStructureNotAnArray;
</ins><span class="cx"> 
</span><del>-        Vector&lt;ContentExtensionRule&gt; ruleList;
-        JSArray* topLevelArray = jsCast&lt;JSArray*&gt;(topLevelObject);
</del><ins>+    JSArray* topLevelArray = jsCast&lt;JSArray*&gt;(topLevelObject);
</ins><span class="cx"> 
</span><del>-        unsigned length = topLevelArray-&gt;length();
-        for (unsigned i = 0; i &lt; length; ++i) {
-            JSValue value = topLevelArray-&gt;getIndex(&amp;exec, i);
-            if (exec.hadException() || !value) {
-                WTFLogAlways(&quot;Invalid object in the array.&quot;);
-                continue;
-            }
</del><ins>+    Vector&lt;ContentExtensionRule&gt; localRuleList;
</ins><span class="cx"> 
</span><del>-            JSObject* ruleObject = value.toObject(&amp;exec);
-            if (!ruleObject || exec.hadException()) {
-                WTFLogAlways(&quot;Invalid rule&quot;);
-                continue;
-            }
-            loadRule(exec, *ruleObject, ruleList);
-        }
-        return ruleList;
</del><ins>+    unsigned length = topLevelArray-&gt;length();
+    for (unsigned i = 0; i &lt; length; ++i) {
+        JSValue value = topLevelArray-&gt;getIndex(&amp;exec, i);
+        if (exec.hadException() || !value)
+            return ContentExtensionError::JSONInvalidObjectInTopLevelArray;
+
+        JSObject* ruleObject = value.toObject(&amp;exec);
+        if (!ruleObject || exec.hadException())
+            return ContentExtensionError::JSONInvalidRule;
+
+        auto error = loadRule(exec, *ruleObject, localRuleList);
+        if (error)
+            return error;
</ins><span class="cx">     }
</span><del>-    return Vector&lt;ContentExtensionRule&gt;();
</del><ins>+
+    ruleList = WTF::move(localRuleList);
+    return { };
</ins><span class="cx"> }
</span><span class="cx"> 
</span><del>-Vector&lt;ContentExtensionRule&gt; parseRuleList(const String&amp; rules)
</del><ins>+std::error_code parseRuleList(const String&amp; rules, Vector&lt;ContentExtensionRule&gt;&amp; ruleList)
</ins><span class="cx"> {
</span><span class="cx"> #if CONTENT_EXTENSIONS_PERFORMANCE_REPORTING
</span><span class="cx">     double loadExtensionStartTime = monotonicallyIncreasingTime();
</span><span class="lines">@@ -219,19 +209,22 @@
</span><span class="cx">     JSGlobalObject* globalObject = JSGlobalObject::create(*vm, JSGlobalObject::createStructure(*vm, jsNull()));
</span><span class="cx"> 
</span><span class="cx">     ExecState* exec = globalObject-&gt;globalExec();
</span><del>-    Vector&lt;ContentExtensionRule&gt; ruleList = loadEncodedRules(*exec, rules);
</del><ins>+    auto error = loadEncodedRules(*exec, rules, ruleList);
</ins><span class="cx"> 
</span><span class="cx">     vm.clear();
</span><span class="cx"> 
</span><ins>+    if (error)
+        return error;
+
</ins><span class="cx">     if (ruleList.isEmpty())
</span><del>-        WTFLogAlways(&quot;Empty extension.&quot;);
</del><ins>+        return ContentExtensionError::JSONContainsNoRules;
</ins><span class="cx"> 
</span><span class="cx"> #if CONTENT_EXTENSIONS_PERFORMANCE_REPORTING
</span><span class="cx">     double loadExtensionEndTime = monotonicallyIncreasingTime();
</span><span class="cx">     dataLogF(&quot;Time spent loading extension %f\n&quot;, (loadExtensionEndTime - loadExtensionStartTime));
</span><span class="cx"> #endif
</span><span class="cx"> 
</span><del>-    return ruleList;
</del><ins>+    return { };
</ins><span class="cx"> }
</span><span class="cx"> 
</span><span class="cx"> } // namespace ContentExtensions
</span></span></pre></div>
<a id="trunkSourceWebCorecontentextensionsContentExtensionParserh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebCore/contentextensions/ContentExtensionParser.h (181973 => 181974)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebCore/contentextensions/ContentExtensionParser.h        2015-03-25 21:33:59 UTC (rev 181973)
+++ trunk/Source/WebCore/contentextensions/ContentExtensionParser.h        2015-03-25 22:38:58 UTC (rev 181974)
</span><span class="lines">@@ -28,6 +28,7 @@
</span><span class="cx"> 
</span><span class="cx"> #if ENABLE(CONTENT_EXTENSIONS)
</span><span class="cx"> 
</span><ins>+#include &lt;system_error&gt;
</ins><span class="cx"> #include &lt;wtf/Forward.h&gt;
</span><span class="cx"> #include &lt;wtf/Vector.h&gt;
</span><span class="cx"> 
</span><span class="lines">@@ -37,7 +38,7 @@
</span><span class="cx"> 
</span><span class="cx"> class ContentExtensionRule;
</span><span class="cx"> 
</span><del>-Vector&lt;ContentExtensionRule&gt; parseRuleList(const String&amp; rules);
</del><ins>+std::error_code parseRuleList(const String&amp; rules, Vector&lt;ContentExtensionRule&gt;&amp;);
</ins><span class="cx"> 
</span><span class="cx"> } // namespace ContentExtensions
</span><span class="cx"> } // namespace WebCore
</span></span></pre></div>
<a id="trunkSourceWebKit2ChangeLog"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit2/ChangeLog (181973 => 181974)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/ChangeLog        2015-03-25 21:33:59 UTC (rev 181973)
+++ trunk/Source/WebKit2/ChangeLog        2015-03-25 22:38:58 UTC (rev 181974)
</span><span class="lines">@@ -1,3 +1,24 @@
</span><ins>+2015-03-25  Sam Weinig  &lt;sam@webkit.org&gt;
+
+        [Content Extensions] Convert content extension compiling to return error codes and write its output using a client
+        https://bugs.webkit.org/show_bug.cgi?id=143059
+
+        Reviewed by Alex Christensen.
+
+        * Shared/WebCompiledContentExtension.cpp:
+        * Shared/WebCompiledContentExtension.h:
+        (WebKit::LegacyContentExtensionCompilationClient::LegacyContentExtensionCompilationClient):
+        (WebKit::LegacyContentExtensionCompilationClient::writeBytecode):
+        (WebKit::LegacyContentExtensionCompilationClient::writeActions):
+        Add subclass of ContentExtensionCompilationClient for use with the non-file backed content
+        extensions.
+
+        * UIProcess/API/C/WKUserContentFilterRef.cpp:
+        (WKUserContentFilterCreate):
+        * UIProcess/API/Cocoa/_WKUserContentFilter.mm:
+        (-[_WKUserContentFilter initWithName:serializedRules:]):
+        Update to use the new interface of compileRuleList().
+
</ins><span class="cx"> 2015-03-25  Ryosuke Niwa  &lt;rniwa@webkit.org&gt;
</span><span class="cx"> 
</span><span class="cx">         Web Inspector: Switching tabs to window with inspector open prohibits typing into console
</span></span></pre></div>
<a id="trunkSourceWebKit2SharedWebCompiledContentExtensioncpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit2/Shared/WebCompiledContentExtension.cpp (181973 => 181974)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/Shared/WebCompiledContentExtension.cpp        2015-03-25 21:33:59 UTC (rev 181973)
+++ trunk/Source/WebKit2/Shared/WebCompiledContentExtension.cpp        2015-03-25 22:38:58 UTC (rev 181974)
</span><span class="lines">@@ -28,10 +28,24 @@
</span><span class="cx"> 
</span><span class="cx"> #if ENABLE(CONTENT_EXTENSIONS)
</span><span class="cx"> 
</span><del>-#include &lt;WebCore/ContentExtensionCompiler.h&gt;
-
</del><span class="cx"> namespace WebKit {
</span><span class="cx"> 
</span><ins>+LegacyContentExtensionCompilationClient::LegacyContentExtensionCompilationClient(WebCore::ContentExtensions::CompiledContentExtensionData&amp; data)
+    : m_data(data)
+{
+}
+
+void LegacyContentExtensionCompilationClient::writeBytecode(Vector&lt;WebCore::ContentExtensions::DFABytecode&gt;&amp;&amp; bytecode)
+{
+    m_data.bytecode = WTF::move(bytecode);
+}
+
+void LegacyContentExtensionCompilationClient::writeActions(Vector&lt;WebCore::ContentExtensions::SerializedActionByte&gt;&amp;&amp; actions)
+{
+    m_data.actions = WTF::move(actions);
+}
+
+
</ins><span class="cx"> Ref&lt;WebCompiledContentExtension&gt; WebCompiledContentExtension::createFromCompiledContentExtensionData(const WebCore::ContentExtensions::CompiledContentExtensionData&amp; compilerData)
</span><span class="cx"> {
</span><span class="cx">     RefPtr&lt;SharedMemory&gt; sharedMemory = SharedMemory::create(compilerData.bytecode.size() + compilerData.actions.size());
</span><span class="lines">@@ -42,7 +56,7 @@
</span><span class="cx">     data.data = WTF::move(sharedMemory);
</span><span class="cx">     data.bytecodeOffset = 0;
</span><span class="cx">     data.bytecodeSize = compilerData.bytecode.size();
</span><del>-    data.actionsOffset = compilerData.bytecode.size();
</del><ins>+    data.actionsOffset = compilerData.  bytecode.size();
</ins><span class="cx">     data.actionsSize = compilerData.actions.size();
</span><span class="cx"> 
</span><span class="cx">     return create(WTF::move(data));
</span></span></pre></div>
<a id="trunkSourceWebKit2SharedWebCompiledContentExtensionh"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit2/Shared/WebCompiledContentExtension.h (181973 => 181974)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/Shared/WebCompiledContentExtension.h        2015-03-25 21:33:59 UTC (rev 181973)
+++ trunk/Source/WebKit2/Shared/WebCompiledContentExtension.h        2015-03-25 22:38:58 UTC (rev 181974)
</span><span class="lines">@@ -29,16 +29,24 @@
</span><span class="cx"> #if ENABLE(CONTENT_EXTENSIONS)
</span><span class="cx"> 
</span><span class="cx"> #include &quot;WebCompiledContentExtensionData.h&quot;
</span><ins>+#include &lt;WebCore/ContentExtensionCompiler.h&gt;
</ins><span class="cx"> #include &lt;WebCore/CompiledContentExtension.h&gt;
</span><span class="cx"> 
</span><del>-namespace WebCore {
-namespace ContentExtensions {
-struct CompiledContentExtensionData;
-}
-}
-
</del><span class="cx"> namespace WebKit {
</span><span class="cx"> 
</span><ins>+// FIXME: Remove this once everyone is converted to using the UserContentExtensionStore.
+class LegacyContentExtensionCompilationClient final : public WebCore::ContentExtensions::ContentExtensionCompilationClient {
+public:
+    LegacyContentExtensionCompilationClient(WebCore::ContentExtensions::CompiledContentExtensionData&amp;);
+
+    virtual void writeBytecode(Vector&lt;WebCore::ContentExtensions::DFABytecode&gt;&amp;&amp;) override;
+    virtual void writeActions(Vector&lt;WebCore::ContentExtensions::SerializedActionByte&gt;&amp;&amp;) override;
+
+private:
+    WebCore::ContentExtensions::CompiledContentExtensionData&amp; m_data;
+};
+
+
</ins><span class="cx"> class WebCompiledContentExtension final : public WebCore::ContentExtensions::CompiledContentExtension {
</span><span class="cx"> public:
</span><span class="cx">     // FIXME: Remove this once everyone is converted to using the UserContentExtensionStore.
</span></span></pre></div>
<a id="trunkSourceWebKit2UIProcessAPICWKUserContentFilterRefcpp"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit2/UIProcess/API/C/WKUserContentFilterRef.cpp (181973 => 181974)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/UIProcess/API/C/WKUserContentFilterRef.cpp        2015-03-25 21:33:59 UTC (rev 181973)
+++ trunk/Source/WebKit2/UIProcess/API/C/WKUserContentFilterRef.cpp        2015-03-25 22:38:58 UTC (rev 181974)
</span><span class="lines">@@ -30,6 +30,7 @@
</span><span class="cx"> #include &quot;WKAPICast.h&quot;
</span><span class="cx"> #include &quot;WebCompiledContentExtension.h&quot;
</span><span class="cx"> #include &lt;WebCore/ContentExtensionCompiler.h&gt;
</span><ins>+#include &lt;WebCore/ContentExtensionError.h&gt;
</ins><span class="cx"> 
</span><span class="cx"> using namespace WebKit;
</span><span class="cx"> 
</span><span class="lines">@@ -41,9 +42,15 @@
</span><span class="cx"> WKUserContentFilterRef WKUserContentFilterCreate(WKStringRef nameRef, WKStringRef serializedRulesRef)
</span><span class="cx"> {
</span><span class="cx"> #if ENABLE(CONTENT_EXTENSIONS)
</span><del>-    auto compiledContentExtensionData = WebCore::ContentExtensions::compileRuleList(toWTFString(serializedRulesRef));
-    auto compiledContentExtension = WebKit::WebCompiledContentExtension::createFromCompiledContentExtensionData(compiledContentExtensionData);
</del><ins>+    WebCore::ContentExtensions::CompiledContentExtensionData data;
+    LegacyContentExtensionCompilationClient client(data);
</ins><span class="cx"> 
</span><ins>+    auto compilerError = WebCore::ContentExtensions::compileRuleList(toWTFString(serializedRulesRef), client);
+    if (compilerError)
+        return nullptr;
+
+    auto compiledContentExtension = WebKit::WebCompiledContentExtension::createFromCompiledContentExtensionData(data);
+
</ins><span class="cx">     return toAPI(&amp;API::UserContentExtension::create(toWTFString(nameRef), WTF::move(compiledContentExtension)).leakRef());
</span><span class="cx"> #else
</span><span class="cx">     UNUSED_PARAM(nameRef);
</span></span></pre></div>
<a id="trunkSourceWebKit2UIProcessAPICocoa_WKUserContentFiltermm"></a>
<div class="modfile"><h4>Modified: trunk/Source/WebKit2/UIProcess/API/Cocoa/_WKUserContentFilter.mm (181973 => 181974)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Source/WebKit2/UIProcess/API/Cocoa/_WKUserContentFilter.mm        2015-03-25 21:33:59 UTC (rev 181973)
+++ trunk/Source/WebKit2/UIProcess/API/Cocoa/_WKUserContentFilter.mm        2015-03-25 22:38:58 UTC (rev 181974)
</span><span class="lines">@@ -30,6 +30,8 @@
</span><span class="cx"> 
</span><span class="cx"> #include &quot;WebCompiledContentExtension.h&quot;
</span><span class="cx"> #include &lt;WebCore/ContentExtensionCompiler.h&gt;
</span><ins>+#include &lt;WebCore/ContentExtensionError.h&gt;
+#include &lt;string&gt;
</ins><span class="cx"> 
</span><span class="cx"> @implementation _WKUserContentFilter
</span><span class="cx"> 
</span><span class="lines">@@ -38,9 +40,14 @@
</span><span class="cx">     if (!(self = [super init]))
</span><span class="cx">         return nil;
</span><span class="cx"> 
</span><del>-    auto compiledContentExtensionData = WebCore::ContentExtensions::compileRuleList(String(serializedRules));
-    auto compiledContentExtension = WebKit::WebCompiledContentExtension::createFromCompiledContentExtensionData(compiledContentExtensionData);
</del><ins>+    WebCore::ContentExtensions::CompiledContentExtensionData data;
+    WebKit::LegacyContentExtensionCompilationClient client(data);
</ins><span class="cx"> 
</span><ins>+    auto compilerError = WebCore::ContentExtensions::compileRuleList(String(serializedRules), client);
+    if (compilerError)
+        [NSException raise:NSGenericException format:@&quot;Failed to compile rules with error: %s&quot;, compilerError.message().c_str()];
+
+    auto compiledContentExtension = WebKit::WebCompiledContentExtension::createFromCompiledContentExtensionData(data);
</ins><span class="cx">     API::Object::constructInWrapper&lt;API::UserContentExtension&gt;(self, String(name), WTF::move(compiledContentExtension));
</span><span class="cx"> 
</span><span class="cx">     return self;
</span></span></pre></div>
<a id="trunkToolsChangeLog"></a>
<div class="modfile"><h4>Modified: trunk/Tools/ChangeLog (181973 => 181974)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Tools/ChangeLog        2015-03-25 21:33:59 UTC (rev 181973)
+++ trunk/Tools/ChangeLog        2015-03-25 22:38:58 UTC (rev 181974)
</span><span class="lines">@@ -1,3 +1,14 @@
</span><ins>+2015-03-25  Sam Weinig  &lt;sam@webkit.org&gt;
+
+        [Content Extensions] Convert content extension compiling to return error codes and write its output using a client
+        https://bugs.webkit.org/show_bug.cgi?id=143059
+
+        Reviewed by Alex Christensen.
+
+        * TestWebKitAPI/Tests/WebCore/ContentExtensions.cpp:
+        (TestWebKitAPI::InMemoryCompiledContentExtension::createFromFilter):
+        Update for new interface of compileRuleList().
+
</ins><span class="cx"> 2015-03-25  Alex Christensen  &lt;achristensen@webkit.org&gt;
</span><span class="cx"> 
</span><span class="cx">         [Content Extensions] Add multi-DFA compiling and interpreting.
</span></span></pre></div>
<a id="trunkToolsTestWebKitAPITestsWebCoreContentExtensionscpp"></a>
<div class="modfile"><h4>Modified: trunk/Tools/TestWebKitAPI/Tests/WebCore/ContentExtensions.cpp (181973 => 181974)</h4>
<pre class="diff"><span>
<span class="info">--- trunk/Tools/TestWebKitAPI/Tests/WebCore/ContentExtensions.cpp        2015-03-25 21:33:59 UTC (rev 181973)
+++ trunk/Tools/TestWebKitAPI/Tests/WebCore/ContentExtensions.cpp        2015-03-25 22:38:58 UTC (rev 181974)
</span><span class="lines">@@ -74,8 +74,40 @@
</span><span class="cx">     }
</span><span class="cx"> };
</span><span class="cx"> 
</span><ins>+class InMemoryContentExtensionCompilationClient final : public WebCore::ContentExtensions::ContentExtensionCompilationClient {
+public:
+    InMemoryContentExtensionCompilationClient(WebCore::ContentExtensions::CompiledContentExtensionData&amp; data)
+        : m_data(data)
+    {
+    }
+
+    virtual void writeBytecode(Vector&lt;WebCore::ContentExtensions::DFABytecode&gt;&amp;&amp; bytecode) override
+    {
+        m_data.bytecode = WTF::move(bytecode);
+    }
+    
+    virtual void writeActions(Vector&lt;WebCore::ContentExtensions::SerializedActionByte&gt;&amp;&amp; actions) override
+    {
+        m_data.actions = WTF::move(actions);
+    }
+
+private:
+    WebCore::ContentExtensions::CompiledContentExtensionData&amp; m_data;
+};
+
</ins><span class="cx"> class InMemoryCompiledContentExtension : public ContentExtensions::CompiledContentExtension {
</span><span class="cx"> public:
</span><ins>+    static RefPtr&lt;InMemoryCompiledContentExtension&gt; createFromFilter(const String&amp; filter)
+    {
+        WebCore::ContentExtensions::CompiledContentExtensionData extensionData;
+        InMemoryContentExtensionCompilationClient client(extensionData);
+        auto compilerError = ContentExtensions::compileRuleList(filter, client);
+        if (compilerError)
+            return nullptr;
+
+        return InMemoryCompiledContentExtension::create(WTF::move(extensionData));
+    }
+
</ins><span class="cx">     static RefPtr&lt;InMemoryCompiledContentExtension&gt; create(ContentExtensions::CompiledContentExtensionData&amp;&amp; data)
</span><span class="cx">     {
</span><span class="cx">         return adoptRef(new InMemoryCompiledContentExtension(WTF::move(data)));
</span><span class="lines">@@ -126,8 +158,7 @@
</span><span class="cx"> 
</span><span class="cx"> TEST_F(ContentExtensionTest, Basic)
</span><span class="cx"> {
</span><del>-    auto extensionData = ContentExtensions::compileRuleList(basicFilter);
-    auto extension = InMemoryCompiledContentExtension::create(WTF::move(extensionData));
</del><ins>+    auto extension = InMemoryCompiledContentExtension::createFromFilter(basicFilter);
</ins><span class="cx"> 
</span><span class="cx">     ContentExtensions::ContentExtensionsBackend backend;
</span><span class="cx">     backend.addContentExtension(&quot;testFilter&quot;, extension);
</span><span class="lines">@@ -139,8 +170,7 @@
</span><span class="cx"> {
</span><span class="cx">     const char* rangeBasicFilter = &quot;[{\&quot;action\&quot;:{\&quot;type\&quot;:\&quot;block\&quot;},\&quot;trigger\&quot;:{\&quot;url-filter\&quot;:\&quot;w[0-9]c\&quot;, \&quot;url-filter-is-case-sensitive\&quot;:true}},&quot;
</span><span class="cx">         &quot;{\&quot;action\&quot;:{\&quot;type\&quot;:\&quot;block-cookies\&quot;},\&quot;trigger\&quot;:{\&quot;url-filter\&quot;:\&quot;[A-H][a-z]cko\&quot;, \&quot;url-filter-is-case-sensitive\&quot;:true}}]&quot;;
</span><del>-    auto extensionData = ContentExtensions::compileRuleList(rangeBasicFilter);
-    auto extension = InMemoryCompiledContentExtension::create(WTF::move(extensionData));
</del><ins>+    auto extension = InMemoryCompiledContentExtension::createFromFilter(rangeBasicFilter);
</ins><span class="cx"> 
</span><span class="cx">     ContentExtensions::ContentExtensionsBackend backend;
</span><span class="cx">     backend.addContentExtension(&quot;PatternNestedGroupsFilter&quot;, extension);
</span><span class="lines">@@ -166,8 +196,7 @@
</span><span class="cx"> {
</span><span class="cx">     // Transition of the type ([^X]X) effictively transition on every input.
</span><span class="cx">     const char* rangeExclusionGeneratingUniversalTransitionFilter = &quot;[{\&quot;action\&quot;:{\&quot;type\&quot;:\&quot;block\&quot;},\&quot;trigger\&quot;:{\&quot;url-filter\&quot;:\&quot;[^a]+afoobar\&quot;}}]&quot;;
</span><del>-    auto extensionData = ContentExtensions::compileRuleList(rangeExclusionGeneratingUniversalTransitionFilter);
-    auto extension = InMemoryCompiledContentExtension::create(WTF::move(extensionData));
</del><ins>+    auto extension = InMemoryCompiledContentExtension::createFromFilter(rangeExclusionGeneratingUniversalTransitionFilter);
</ins><span class="cx"> 
</span><span class="cx">     ContentExtensions::ContentExtensionsBackend backend;
</span><span class="cx">     backend.addContentExtension(&quot;PatternNestedGroupsFilter&quot;, extension);
</span><span class="lines">@@ -189,8 +218,7 @@
</span><span class="cx"> TEST_F(ContentExtensionTest, PatternStartingWithGroup)
</span><span class="cx"> {
</span><span class="cx">     const char* patternsStartingWithGroupFilter = &quot;[{\&quot;action\&quot;:{\&quot;type\&quot;:\&quot;block\&quot;},\&quot;trigger\&quot;:{\&quot;url-filter\&quot;:\&quot;^(http://whatwg\\\\.org/)?webkit\134\134.org\&quot;}}]&quot;;
</span><del>-    auto extensionData = ContentExtensions::compileRuleList(patternsStartingWithGroupFilter);
-    auto extension = InMemoryCompiledContentExtension::create(WTF::move(extensionData));
</del><ins>+    auto extension = InMemoryCompiledContentExtension::createFromFilter(patternsStartingWithGroupFilter);
</ins><span class="cx"> 
</span><span class="cx">     ContentExtensions::ContentExtensionsBackend backend;
</span><span class="cx">     backend.addContentExtension(&quot;PatternNestedGroupsFilter&quot;, extension);
</span><span class="lines">@@ -206,8 +234,7 @@
</span><span class="cx"> {
</span><span class="cx">     const char* patternNestedGroupsFilter = &quot;[{\&quot;action\&quot;:{\&quot;type\&quot;:\&quot;block\&quot;},\&quot;trigger\&quot;:{\&quot;url-filter\&quot;:\&quot;^http://webkit\\\\.org/(foo(bar)*)+\&quot;}}]&quot;;
</span><span class="cx"> 
</span><del>-    auto extensionData = ContentExtensions::compileRuleList(patternNestedGroupsFilter);
-    auto extension = InMemoryCompiledContentExtension::create(WTF::move(extensionData));
</del><ins>+    auto extension = InMemoryCompiledContentExtension::createFromFilter(patternNestedGroupsFilter);
</ins><span class="cx"> 
</span><span class="cx">     ContentExtensions::ContentExtensionsBackend backend;
</span><span class="cx">     backend.addContentExtension(&quot;PatternNestedGroupsFilter&quot;, extension);
</span><span class="lines">@@ -229,8 +256,7 @@
</span><span class="cx"> {
</span><span class="cx">     const char* matchPastEndOfStringFilter = &quot;[{\&quot;action\&quot;:{\&quot;type\&quot;:\&quot;block\&quot;},\&quot;trigger\&quot;:{\&quot;url-filter\&quot;:\&quot;.+\&quot;}}]&quot;;
</span><span class="cx"> 
</span><del>-    auto extensionData = ContentExtensions::compileRuleList(matchPastEndOfStringFilter);
-    auto extension = InMemoryCompiledContentExtension::create(WTF::move(extensionData));
</del><ins>+    auto extension = InMemoryCompiledContentExtension::createFromFilter(matchPastEndOfStringFilter);
</ins><span class="cx"> 
</span><span class="cx">     ContentExtensions::ContentExtensionsBackend backend;
</span><span class="cx">     backend.addContentExtension(&quot;MatchPastEndOfString&quot;, extension);
</span><span class="lines">@@ -249,8 +275,7 @@
</span><span class="cx"> 
</span><span class="cx"> TEST_F(ContentExtensionTest, StartOfLineAssertion)
</span><span class="cx"> {
</span><del>-    auto extensionData = ContentExtensions::compileRuleList(startOfLineAssertionFilter);
-    auto extension = InMemoryCompiledContentExtension::create(WTF::move(extensionData));
</del><ins>+    auto extension = InMemoryCompiledContentExtension::createFromFilter(startOfLineAssertionFilter);
</ins><span class="cx"> 
</span><span class="cx">     ContentExtensions::ContentExtensionsBackend backend;
</span><span class="cx">     backend.addContentExtension(&quot;StartOfLineAssertion&quot;, extension);
</span><span class="lines">@@ -268,8 +293,7 @@
</span><span class="cx"> TEST_F(ContentExtensionTest, EndOfLineAssertion)
</span><span class="cx"> {
</span><span class="cx">     const char* endOfLineAssertionFilter = &quot;[{\&quot;action\&quot;:{\&quot;type\&quot;:\&quot;block\&quot;},\&quot;trigger\&quot;:{\&quot;url-filter\&quot;:\&quot;foobar$\&quot;}}]&quot;;
</span><del>-    auto extensionData = ContentExtensions::compileRuleList(endOfLineAssertionFilter);
-    auto extension = InMemoryCompiledContentExtension::create(WTF::move(extensionData));
</del><ins>+    auto extension = InMemoryCompiledContentExtension::createFromFilter(endOfLineAssertionFilter);
</ins><span class="cx"> 
</span><span class="cx">     ContentExtensions::ContentExtensionsBackend backend;
</span><span class="cx">     backend.addContentExtension(&quot;EndOfLineAssertion&quot;, extension);
</span><span class="lines">@@ -285,8 +309,7 @@
</span><span class="cx"> TEST_F(ContentExtensionTest, EndOfLineAssertionWithInvertedCharacterSet)
</span><span class="cx"> {
</span><span class="cx">     const char* endOfLineAssertionWithInvertedCharacterSetFilter = &quot;[{\&quot;action\&quot;:{\&quot;type\&quot;:\&quot;block\&quot;},\&quot;trigger\&quot;:{\&quot;url-filter\&quot;:\&quot;[^y]$\&quot;}}]&quot;;
</span><del>-    auto extensionData = ContentExtensions::compileRuleList(endOfLineAssertionWithInvertedCharacterSetFilter);
-    auto extension = InMemoryCompiledContentExtension::create(WTF::move(extensionData));
</del><ins>+    auto extension = InMemoryCompiledContentExtension::createFromFilter(endOfLineAssertionWithInvertedCharacterSetFilter);
</ins><span class="cx"> 
</span><span class="cx">     ContentExtensions::ContentExtensionsBackend backend;
</span><span class="cx">     backend.addContentExtension(&quot;EndOfLineAssertion&quot;, extension);
</span><span class="lines">@@ -308,8 +331,7 @@
</span><span class="cx">         &quot;{\&quot;action\&quot;:{\&quot;type\&quot;:\&quot;block\&quot;},\&quot;trigger\&quot;:{\&quot;url-filter\&quot;:\&quot;^prefix\&quot;}},&quot;
</span><span class="cx">         &quot;{\&quot;action\&quot;:{\&quot;type\&quot;:\&quot;block\&quot;},\&quot;trigger\&quot;:{\&quot;url-filter\&quot;:\&quot;suffix$\&quot;}},&quot;
</span><span class="cx">         &quot;{\&quot;action\&quot;:{\&quot;type\&quot;:\&quot;block\&quot;},\&quot;trigger\&quot;:{\&quot;url-filter\&quot;:\&quot;^http://exact\\\\.org/$\&quot;}}]&quot;;
</span><del>-    auto extensionData = ContentExtensions::compileRuleList(prefixInfixSuffixExactMatchFilter);
-    auto extension = InMemoryCompiledContentExtension::create(WTF::move(extensionData));
</del><ins>+    auto extension = InMemoryCompiledContentExtension::createFromFilter(prefixInfixSuffixExactMatchFilter);
</ins><span class="cx"> 
</span><span class="cx">     ContentExtensions::ContentExtensionsBackend backend;
</span><span class="cx">     backend.addContentExtension(&quot;PrefixInfixSuffixExactMatch&quot;, extension);
</span><span class="lines">@@ -334,8 +356,7 @@
</span><span class="cx"> {
</span><span class="cx">     const char* duplicatedMatchAllTermsInVariousFormatFilter = &quot;[{\&quot;action\&quot;:{\&quot;type\&quot;:\&quot;block\&quot;},\&quot;trigger\&quot;:{\&quot;url-filter\&quot;:\&quot;.*.*(.)*(.*)(.+)*(.?)*infix\&quot;}},&quot;
</span><span class="cx">         &quot;{\&quot;action\&quot;:{\&quot;type\&quot;:\&quot;block\&quot;},\&quot;trigger\&quot;:{\&quot;url-filter\&quot;:\&quot;pre(.?)+(.+)?post\&quot;}}]&quot;;
</span><del>-    auto extensionData = ContentExtensions::compileRuleList(duplicatedMatchAllTermsInVariousFormatFilter);
-    auto extension = InMemoryCompiledContentExtension::create(WTF::move(extensionData));
</del><ins>+    auto extension = InMemoryCompiledContentExtension::createFromFilter(duplicatedMatchAllTermsInVariousFormatFilter);
</ins><span class="cx"> 
</span><span class="cx">     ContentExtensions::ContentExtensionsBackend backend;
</span><span class="cx">     backend.addContentExtension(&quot;DuplicatedMatchAllTermsInVariousFormat&quot;, extension);
</span><span class="lines">@@ -367,8 +388,7 @@
</span><span class="cx">         &quot;{\&quot;action\&quot;:{\&quot;type\&quot;:\&quot;block\&quot;},\&quot;trigger\&quot;:{\&quot;url-filter\&quot;:\&quot;^pre8(.?)*post8$\&quot;}},&quot;
</span><span class="cx">         &quot;{\&quot;action\&quot;:{\&quot;type\&quot;:\&quot;block\&quot;},\&quot;trigger\&quot;:{\&quot;url-filter\&quot;:\&quot;^pre9(.+)?post9$\&quot;}},&quot;
</span><span class="cx">         &quot;{\&quot;action\&quot;:{\&quot;type\&quot;:\&quot;block\&quot;},\&quot;trigger\&quot;:{\&quot;url-filter\&quot;:\&quot;^pre0(.?)+post0$\&quot;}}]&quot;;
</span><del>-    auto extensionData = ContentExtensions::compileRuleList(termsKnownToMatchAnythingFilter);
-    auto extension = InMemoryCompiledContentExtension::create(WTF::move(extensionData));
</del><ins>+    auto extension = InMemoryCompiledContentExtension::createFromFilter(termsKnownToMatchAnythingFilter);
</ins><span class="cx"> 
</span><span class="cx">     ContentExtensions::ContentExtensionsBackend backend;
</span><span class="cx">     backend.addContentExtension(&quot;TermsKnownToMatchAnything&quot;, extension);
</span><span class="lines">@@ -411,8 +431,7 @@
</span><span class="cx"> {
</span><span class="cx">     const char* trailingDotStarFilter = &quot;[{\&quot;action\&quot;:{\&quot;type\&quot;:\&quot;block\&quot;},\&quot;trigger\&quot;:{\&quot;url-filter\&quot;:\&quot;foo.*$\&quot;}},&quot;
</span><span class="cx">         &quot;{\&quot;action\&quot;:{\&quot;type\&quot;:\&quot;block\&quot;},\&quot;trigger\&quot;:{\&quot;url-filter\&quot;:\&quot;bar(.*)$\&quot;}}]&quot;;
</span><del>-    auto extensionData = ContentExtensions::compileRuleList(trailingDotStarFilter);
-    auto extension = InMemoryCompiledContentExtension::create(WTF::move(extensionData));
</del><ins>+    auto extension = InMemoryCompiledContentExtension::createFromFilter(trailingDotStarFilter);
</ins><span class="cx"> 
</span><span class="cx">     ContentExtensions::ContentExtensionsBackend backend;
</span><span class="cx">     backend.addContentExtension(&quot;TrailingDotStar&quot;, extension);
</span><span class="lines">@@ -435,8 +454,7 @@
</span><span class="cx">     const char* trailingTermsCarryingNoDataFilter = &quot;[{\&quot;action\&quot;:{\&quot;type\&quot;:\&quot;block\&quot;},\&quot;trigger\&quot;:{\&quot;url-filter\&quot;:\&quot;foob?a?r?\&quot;}},&quot;
</span><span class="cx">         &quot;{\&quot;action\&quot;:{\&quot;type\&quot;:\&quot;block\&quot;},\&quot;trigger\&quot;:{\&quot;url-filter\&quot;:\&quot;bazo(ok)?a?$\&quot;}},&quot;
</span><span class="cx">         &quot;{\&quot;action\&quot;:{\&quot;type\&quot;:\&quot;block\&quot;},\&quot;trigger\&quot;:{\&quot;url-filter\&quot;:\&quot;cats*$\&quot;}}]&quot;;
</span><del>-    auto extensionData = ContentExtensions::compileRuleList(trailingTermsCarryingNoDataFilter);
-    auto extension = InMemoryCompiledContentExtension::create(WTF::move(extensionData));
</del><ins>+    auto extension = InMemoryCompiledContentExtension::createFromFilter(trailingTermsCarryingNoDataFilter);
</ins><span class="cx"> 
</span><span class="cx">     ContentExtensions::ContentExtensionsBackend backend;
</span><span class="cx">     backend.addContentExtension(&quot;TrailingTermsCarryingNoData&quot;, extension);
</span><span class="lines">@@ -478,8 +496,7 @@
</span><span class="cx">         &quot;{\&quot;action\&quot;:{\&quot;type\&quot;:\&quot;block\&quot;},\&quot;trigger\&quot;:{\&quot;url-filter\&quot;:\&quot;whatwg.org\&quot;,\&quot;load-type\&quot;:[\&quot;first-party\&quot;]}},&quot;
</span><span class="cx">         &quot;{\&quot;action\&quot;:{\&quot;type\&quot;:\&quot;block\&quot;},\&quot;trigger\&quot;:{\&quot;url-filter\&quot;:\&quot;alwaysblock.pdf\&quot;}}]&quot;;
</span><span class="cx"> 
</span><del>-    auto extensionData = ContentExtensions::compileRuleList(loadTypeFilter);
-    auto extension = InMemoryCompiledContentExtension::create(WTF::move(extensionData));
</del><ins>+    auto extension = InMemoryCompiledContentExtension::createFromFilter(loadTypeFilter);
</ins><span class="cx">         
</span><span class="cx">     ContentExtensions::ContentExtensionsBackend backend;
</span><span class="cx">     backend.addContentExtension(&quot;LoadTypeFilter&quot;, extension);
</span><span class="lines">@@ -499,8 +516,7 @@
</span><span class="cx">     const char* resourceTypeFilter = &quot;[{\&quot;action\&quot;:{\&quot;type\&quot;:\&quot;block\&quot;},\&quot;trigger\&quot;:{\&quot;url-filter\&quot;:\&quot;block_all_types.org\&quot;,\&quot;resource-type\&quot;:[\&quot;document\&quot;,\&quot;image\&quot;,\&quot;style-sheet\&quot;,\&quot;script\&quot;,\&quot;font\&quot;,\&quot;raw\&quot;,\&quot;svg-document\&quot;,\&quot;media\&quot;]}},&quot;
</span><span class="cx">         &quot;{\&quot;action\&quot;:{\&quot;type\&quot;:\&quot;block\&quot;},\&quot;trigger\&quot;:{\&quot;url-filter\&quot;:\&quot;block_only_images\&quot;,\&quot;resource-type\&quot;:[\&quot;image\&quot;]}}]&quot;;
</span><span class="cx"> 
</span><del>-    auto extensionData = ContentExtensions::compileRuleList(resourceTypeFilter);
-    auto extension = InMemoryCompiledContentExtension::create(WTF::move(extensionData));
</del><ins>+    auto extension = InMemoryCompiledContentExtension::createFromFilter(resourceTypeFilter);
</ins><span class="cx">         
</span><span class="cx">     ContentExtensions::ContentExtensionsBackend backend;
</span><span class="cx">     backend.addContentExtension(&quot;ResourceTypeFilter&quot;, extension);
</span><span class="lines">@@ -545,8 +561,7 @@
</span><span class="cx">     }
</span><span class="cx">     ruleList.append(']');
</span><span class="cx">     
</span><del>-    auto extensionData = ContentExtensions::compileRuleList(ruleList.toString());
-    auto extension = InMemoryCompiledContentExtension::create(WTF::move(extensionData));
</del><ins>+    auto extension = InMemoryCompiledContentExtension::createFromFilter(ruleList.toString());
</ins><span class="cx">         
</span><span class="cx">     ContentExtensions::ContentExtensionsBackend backend;
</span><span class="cx">     backend.addContentExtension(&quot;ResourceTypeFilter&quot;, extension);
</span></span></pre>
</div>
</div>

</body>
</html>