[SCM] WebKit Debian packaging branch, webkit-1.2, updated. upstream/1.1.90-6072-g9a69373

eric at webkit.org eric at webkit.org
Thu Apr 8 01:58:56 UTC 2010


The following commit has been merged in the webkit-1.2 branch:
commit 700c5b0d2832d6d607e0d9dac3fb71cdde912887
Author: eric at webkit.org <eric at webkit.org@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Date:   Thu Feb 25 11:24:53 2010 +0000

    2010-02-25  Andrey Kosyakov  <caseq at chromium.org>
    
            Reviewed by Pavel Feldman.
    
            Fake workers implementation that simulates workers using iframe and timer,
            needed to support workers debugging. Also, a facility to inject scripts into
            inspected page upon load.
            https://bugs.webkit.org/show_bug.cgi?id=35148
    
            * WebCore.gypi:
            * WebCore.vcproj/WebCore.vcproj:
            * inspector/InspectorBackend.cpp:
            (WebCore::InspectorBackend::addScriptToEvaluateOnLoad):
            (WebCore::InspectorBackend::removeAllScriptsToEvaluateOnLoad):
            * inspector/InspectorBackend.h:
            * inspector/InspectorBackend.idl:
            * inspector/InspectorController.cpp:
            (WebCore::InspectorController::didCommitLoad):
            (WebCore::InspectorController::addScriptToEvaluateOnLoad):
            (WebCore::InspectorController::removeAllScriptsToEvaluateOnLoad):
            * inspector/InspectorController.h:
            * inspector/front-end/InjectedFakeWorker.js: Added.
            (InjectedFakeWorker.Worker):
            (InjectedFakeWorker.FakeWorker):
            (InjectedFakeWorker.FakeWorker.prototype.postMessage):
            (InjectedFakeWorker.FakeWorker.prototype.terminate):
            (InjectedFakeWorker.FakeWorker.prototype._onmessageWrapper):
            (InjectedFakeWorker.FakeWorker.prototype._dispatchMessage):
            (InjectedFakeWorker.FakeWorker.prototype._handleException):
            (InjectedFakeWorker.FakeWorker.prototype._buildWorker):
            (InjectedFakeWorker.FakeWorker.prototype._setupWorkerContext.handler):
            (InjectedFakeWorker.FakeWorker.prototype._setupWorkerContext):
            (InjectedFakeWorker.FakeWorker.prototype._importScripts):
            (InjectedFakeWorker.FakeWorker.prototype._loadScript):
            (InjectedFakeWorker.URL):
            (InjectedFakeWorker.URL.prototype.urlRegEx.split):
            (InjectedFakeWorker.URL.prototype.mockLocation):
            (InjectedFakeWorker.URL.prototype.completeWith):
            (InjectedFakeWorker.URL.prototype.sameOrigin):
            (InjectedFakeWorker.DOMCoreException.formatError):
            (InjectedFakeWorker.DOMCoreException):
            (InjectedFakeWorker.noop):
            * inspector/front-end/InspectorBackendStub.js:
            (.WebInspector.InspectorBackendStub.prototype.setInjectedScriptSource):
            (.WebInspector.InspectorBackendStub.prototype.addScriptToEvaluateOnLoad):
            (.WebInspector.InspectorBackendStub.prototype.removeAllScriptsToEvaluateOnLoad):
            * inspector/front-end/WebKit.qrc:
            * inspector/front-end/inspector.html:
    
    git-svn-id: http://svn.webkit.org/repository/webkit/trunk@55227 268f45cc-cd09-0410-ab3c-d52691b4dbfc

diff --git a/WebCore/ChangeLog b/WebCore/ChangeLog
index f6ab9ff..aeae057 100644
--- a/WebCore/ChangeLog
+++ b/WebCore/ChangeLog
@@ -1,3 +1,52 @@
+2010-02-25  Andrey Kosyakov  <caseq at chromium.org>
+
+        Reviewed by Pavel Feldman.
+
+        Fake workers implementation that simulates workers using iframe and timer,
+        needed to support workers debugging. Also, a facility to inject scripts into
+        inspected page upon load.
+        https://bugs.webkit.org/show_bug.cgi?id=35148
+
+        * WebCore.gypi:
+        * WebCore.vcproj/WebCore.vcproj:
+        * inspector/InspectorBackend.cpp:
+        (WebCore::InspectorBackend::addScriptToEvaluateOnLoad):
+        (WebCore::InspectorBackend::removeAllScriptsToEvaluateOnLoad):
+        * inspector/InspectorBackend.h:
+        * inspector/InspectorBackend.idl:
+        * inspector/InspectorController.cpp:
+        (WebCore::InspectorController::didCommitLoad):
+        (WebCore::InspectorController::addScriptToEvaluateOnLoad):
+        (WebCore::InspectorController::removeAllScriptsToEvaluateOnLoad):
+        * inspector/InspectorController.h:
+        * inspector/front-end/InjectedFakeWorker.js: Added.
+        (InjectedFakeWorker.Worker):
+        (InjectedFakeWorker.FakeWorker):
+        (InjectedFakeWorker.FakeWorker.prototype.postMessage):
+        (InjectedFakeWorker.FakeWorker.prototype.terminate):
+        (InjectedFakeWorker.FakeWorker.prototype._onmessageWrapper):
+        (InjectedFakeWorker.FakeWorker.prototype._dispatchMessage):
+        (InjectedFakeWorker.FakeWorker.prototype._handleException):
+        (InjectedFakeWorker.FakeWorker.prototype._buildWorker):
+        (InjectedFakeWorker.FakeWorker.prototype._setupWorkerContext.handler):
+        (InjectedFakeWorker.FakeWorker.prototype._setupWorkerContext):
+        (InjectedFakeWorker.FakeWorker.prototype._importScripts):
+        (InjectedFakeWorker.FakeWorker.prototype._loadScript):
+        (InjectedFakeWorker.URL):
+        (InjectedFakeWorker.URL.prototype.urlRegEx.split):
+        (InjectedFakeWorker.URL.prototype.mockLocation):
+        (InjectedFakeWorker.URL.prototype.completeWith):
+        (InjectedFakeWorker.URL.prototype.sameOrigin):
+        (InjectedFakeWorker.DOMCoreException.formatError):
+        (InjectedFakeWorker.DOMCoreException):
+        (InjectedFakeWorker.noop):
+        * inspector/front-end/InspectorBackendStub.js:
+        (.WebInspector.InspectorBackendStub.prototype.setInjectedScriptSource):
+        (.WebInspector.InspectorBackendStub.prototype.addScriptToEvaluateOnLoad):
+        (.WebInspector.InspectorBackendStub.prototype.removeAllScriptsToEvaluateOnLoad):
+        * inspector/front-end/WebKit.qrc:
+        * inspector/front-end/inspector.html:
+
 2010-02-24  Nicholas Young  <nicholas.young at nokia.com>
 
         Reviewed by Eric Carlson.
diff --git a/WebCore/WebCore.gypi b/WebCore/WebCore.gypi
index b3bd08a..4c99bc1 100644
--- a/WebCore/WebCore.gypi
+++ b/WebCore/WebCore.gypi
@@ -3746,6 +3746,7 @@
             'inspector/front-end/ImageView.js',
             'inspector/front-end/InspectorBackendStub.js',
             'inspector/front-end/InspectorFrontendHostStub.js',
+            'inspector/front-end/InjectedFakeWorker.js',
             'inspector/front-end/InjectedScript.js',
             'inspector/front-end/InjectedScriptAccess.js',
             'inspector/front-end/inspector.js',
diff --git a/WebCore/WebCore.vcproj/WebCore.vcproj b/WebCore/WebCore.vcproj/WebCore.vcproj
index e537e35..32bb1c7 100644
--- a/WebCore/WebCore.vcproj/WebCore.vcproj
+++ b/WebCore/WebCore.vcproj/WebCore.vcproj
@@ -42856,6 +42856,10 @@
 					>
 				</File>
 				<File
+					RelativePath="..\inspector\front-end\InjectedFakeWorker.js"
+					>
+				</File>
+				<File
 					RelativePath="..\inspector\front-end\InjectedScript.js"
 					>
 				</File>
diff --git a/WebCore/inspector/InspectorBackend.cpp b/WebCore/inspector/InspectorBackend.cpp
index 774e569..7e86443 100644
--- a/WebCore/inspector/InspectorBackend.cpp
+++ b/WebCore/inspector/InspectorBackend.cpp
@@ -469,6 +469,18 @@ Node* InspectorBackend::nodeForId(long nodeId)
     return 0;
 }
 
+void InspectorBackend::addScriptToEvaluateOnLoad(const String& source)
+{
+    if (m_inspectorController)
+        m_inspectorController->addScriptToEvaluateOnLoad(source);
+}
+
+void InspectorBackend::removeAllScriptsToEvaluateOnLoad()
+{
+    if (m_inspectorController)
+        m_inspectorController->removeAllScriptsToEvaluateOnLoad();
+}
+
 } // namespace WebCore
 
 #endif // ENABLE(INSPECTOR)
diff --git a/WebCore/inspector/InspectorBackend.h b/WebCore/inspector/InspectorBackend.h
index 8a8c203..a9fd8ca 100644
--- a/WebCore/inspector/InspectorBackend.h
+++ b/WebCore/inspector/InspectorBackend.h
@@ -105,6 +105,8 @@ public:
 
     void setInjectedScriptSource(const String& source);
     void dispatchOnInjectedScript(long callId, long injectedScriptId, const String& methodName, const String& arguments, bool async);
+    void addScriptToEvaluateOnLoad(const String& source);
+    void removeAllScriptsToEvaluateOnLoad();
     void getChildNodes(long callId, long nodeId);
     void setAttribute(long callId, long elementId, const String& name, const String& value);
     void removeAttribute(long callId, long elementId, const String& name);
diff --git a/WebCore/inspector/InspectorBackend.idl b/WebCore/inspector/InspectorBackend.idl
index e65f94a..753fd86 100644
--- a/WebCore/inspector/InspectorBackend.idl
+++ b/WebCore/inspector/InspectorBackend.idl
@@ -80,6 +80,9 @@ module core {
         void setInjectedScriptSource(in DOMString scriptSource);
         void dispatchOnInjectedScript(in long callId, in long injectedScriptId, in DOMString methodName, in DOMString arguments, in boolean async);
 
+        void addScriptToEvaluateOnLoad(in DOMString scriptSource);
+        void removeAllScriptsToEvaluateOnLoad();
+
         void getChildNodes(in long callId, in long nodeId);
         void setAttribute(in long callId, in long elementId, in DOMString name, in DOMString value);
         void removeAttribute(in long callId, in long elementId, in DOMString name);
diff --git a/WebCore/inspector/InspectorController.cpp b/WebCore/inspector/InspectorController.cpp
index e8d90c6..51dd4a8 100644
--- a/WebCore/inspector/InspectorController.cpp
+++ b/WebCore/inspector/InspectorController.cpp
@@ -76,6 +76,7 @@
 #include "ScriptObject.h"
 #include "ScriptProfile.h"
 #include "ScriptProfiler.h"
+#include "ScriptSourceCode.h"
 #include "ScriptString.h"
 #include "SecurityOrigin.h"
 #include "Settings.h"
@@ -802,6 +803,12 @@ void InspectorController::didCommitLoad(DocumentLoader* loader)
     for (Frame* frame = loader->frame(); frame; frame = frame->tree()->traverseNext(loader->frame()))
         if (ResourcesMap* resourceMap = m_frameResources.get(frame))
             pruneResources(resourceMap, loader);
+
+    for (Vector<String>::iterator it = m_scriptsToEvaluateOnLoad.begin();
+         it != m_scriptsToEvaluateOnLoad.end(); ++it) {
+        ScriptSourceCode scriptSourceCode(*it);
+        loader->frame()->script()->evaluate(scriptSourceCode);
+    }
 }
 
 void InspectorController::frameDetachedFromParent(Frame* frame)
@@ -1900,6 +1907,16 @@ InjectedScript InspectorController::injectedScriptForNodeId(long id)
     return InjectedScript();
 }
 
+void InspectorController::addScriptToEvaluateOnLoad(const String& source)
+{
+    m_scriptsToEvaluateOnLoad.append(source);
+}
+
+void InspectorController::removeAllScriptsToEvaluateOnLoad()
+{
+    m_scriptsToEvaluateOnLoad.clear();
+}
+
 } // namespace WebCore
     
 #endif // ENABLE(INSPECTOR)
diff --git a/WebCore/inspector/InspectorController.h b/WebCore/inspector/InspectorController.h
index cfbe4b5..500b0df 100644
--- a/WebCore/inspector/InspectorController.h
+++ b/WebCore/inspector/InspectorController.h
@@ -250,6 +250,8 @@ public:
     void evaluateForTestInFrontend(long callId, const String& script);
 
     InjectedScript injectedScriptForNodeId(long id);
+    void addScriptToEvaluateOnLoad(const String& source);
+    void removeAllScriptsToEvaluateOnLoad();
 
 private:
     static const char* const FrontendSettingsSettingName;
@@ -349,6 +351,7 @@ private:
     mutable Settings m_settings;
 
     Vector<pair<long, String> > m_pendingEvaluateTestCommands;
+    Vector<String> m_scriptsToEvaluateOnLoad;
 #if ENABLE(JAVASCRIPT_DEBUGGER)
     bool m_debuggerEnabled;
     bool m_attachDebuggerWhenShown;
diff --git a/WebCore/inspector/front-end/InjectedFakeWorker.js b/WebCore/inspector/front-end/InjectedFakeWorker.js
new file mode 100644
index 0000000..ecaa64a
--- /dev/null
+++ b/WebCore/inspector/front-end/InjectedFakeWorker.js
@@ -0,0 +1,264 @@
+/*
+ * Copyright (C) 2010 Google 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:
+ *
+ *     * Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ *     * 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.
+ *     * Neither the name of Google Inc. nor the names of its
+ * contributors may be used to endorse or promote products derived from
+ * this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND 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 THE COPYRIGHT
+ * OWNER OR 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.
+ */
+
+var InjectedFakeWorker = function()
+{
+
+Worker = function(url)
+{
+    var impl = new FakeWorker(this, url);
+    if (impl === null)
+        return null;
+
+    this.isFake = true;
+    this.postMessage = bind(impl.postMessage, impl);
+    this.terminate = bind(impl.terminate, impl);
+    this.onmessage = noop;
+}
+
+function FakeWorker(worker, url)
+{
+    var scriptURL = new URL(document.baseURI).completeWith(url);
+
+    if (!scriptURL.sameOrigin(location.href))
+        throw new DOMCoreException("SECURITY_ERR",18);
+
+    this._worker = worker;
+    this._buildWorker(scriptURL);
+}
+
+FakeWorker.prototype = {
+    postMessage: function(msg)
+    {
+        if (this._frame != null)
+            this._dispatchMessage(this._frame, bind(this._onmessageWrapper, this), msg);
+    },
+
+    terminate: function()
+    {
+        if (this._frame != null) {
+            this._frame.onmessage = this._worker.onmessage = noop;
+            this._frame.frameElement.parentNode.removeChild(this._frame.frameElement);
+        }
+        this._frame = null;
+        this._worker = null; // Break reference loop.
+    },
+
+    _onmessageWrapper: function(msg)
+    {
+        // Shortcut -- if no exception handlers installed, avoid try/catch so as not to obscure line number.
+        if (!this._frame.onerror && !this._worker.onerror) {
+            this._frame.onmessage(msg);
+            return;
+        }
+
+        try {
+            this._frame.onmessage(msg);
+        } catch (e) {
+            this._handleException(e, this._frame.onerror, this._worker.onerror);
+        }
+    },
+
+    _dispatchMessage: function(targetWindow, handler, msg)
+    {
+        var event = this._document.createEvent("MessageEvent");
+        event.initMessageEvent("MessageEvent", false, false, msg);
+        targetWindow.setTimeout(handler, 0, event);
+    },
+
+    _handleException: function(e)
+    {
+        // NB: it should be an ErrorEvent, but creating it from script is not
+        // currently supported, to emulate it on top of plain vanilla Event.
+        var errorEvent = this._document.createEvent("Event");
+        errorEvent.initEvent("Event", false, false);
+        errorEvent.message = "Uncaught exception";
+
+        for (var i = 1; i < arguments.length; ++i) {
+            if (arguments[i] && arguments[i](errorEvent))
+                return;
+        }
+
+        throw e;
+    },
+
+    _buildWorker: function(url)
+    {
+        var code = this._loadScript(url.url);
+        var iframeElement = document.createElement("iframe");
+        iframeElement.style.display = "none";
+        document.body.appendChild(iframeElement);
+
+        var frame = window.frames[window.frames.length - 1];
+
+        this._document = document;
+        this._frame = frame;
+
+        this._setupWorkerContext(frame, url);
+
+        var frameContents = '(function(location, window) { ' + code + '})(__devtools.location, undefined);\n' + '//@ sourceURL=' + url.url;
+
+        frame.eval(frameContents);
+    },
+
+    _setupWorkerContext: function(workerFrame, url)
+    {
+        workerFrame.__devtools = {
+            handleException: bind(this._handleException, this),
+            location: url.mockLocation()
+        };
+        var worker = this._worker;
+
+        function handler(event) // Late binding to onmessage desired, so no bind() here.
+        {
+            worker.onmessage(event);
+        }
+
+        workerFrame.onmessage = noop;
+        workerFrame.postMessage = bind(this._dispatchMessage, this, window, handler);
+        workerFrame.importScripts = bind(this._importScripts, this, workerFrame);
+        workerFrame.close = bind(this.terminate, this);
+    },
+
+    _importScripts: function(evalTarget)
+    {
+        for (var i = 1; i < arguments.length; ++i)
+            evalTarget.eval(this._loadScript(arguments[i]));
+    },
+
+    _loadScript: function(url)
+    {
+        var xhr = new XMLHttpRequest();
+        xhr.open("GET", url, false);
+        xhr.send(null);
+
+        var text = xhr.responseText;
+        if (xhr.status != 0 && xhr.status/100 !== 2) { // We're getting status === 0 when using file://.
+            console.error("Failed to load worker: " + url + "[" + xhr.status + "]");
+            text = ""; // We've got error message, not worker code.
+        }
+        return text;
+    }
+};
+
+function URL(url)
+{
+    this.url = url;
+    this.split();
+}
+
+URL.prototype = {
+    urlRegEx: (/^(http[s]?|file):\/\/([^\/:]*)(:[\d]+)?(?:(\/[^#?]*)(\?[^#]*)?(?:#(.*))?)?$/i),
+
+    split: function()
+    {
+        function emptyIfNull(str)
+        {
+            return str == null ? "" : str;
+        }
+        var parts = this.urlRegEx.exec(this.url);
+
+        this.schema = parts[1];
+        this.host = parts[2];
+        this.port = emptyIfNull(parts[3]);
+        this.path = emptyIfNull(parts[4]);
+        this.query = emptyIfNull(parts[5]);
+        this.fragment = emptyIfNull(parts[6]);
+    },
+
+    mockLocation: function()
+    {
+        var host = this.host.replace(/^[^@]*@/, "");
+
+        return {
+            href:     this.url,
+            protocol: this.schema + ":",
+            host:     host,
+            hostname: host,
+            port:     this.port,
+            pathname: this.path,
+            search:   this.query,
+            hash:     this.fragment
+        };
+    },
+
+    completeWith: function(url)
+    {
+        if (url === "" || /^[^/]*:/.exec(url)) // If given absolute url, return as is now.
+            return new URL(url);
+
+        var relParts = /^([^#?]*)(.*)$/.exec(url); // => [ url, path, query-andor-fragment ]
+
+        var path = (relParts[1].slice(0, 1) === "/" ? "" : this.path.replace(/[^/]*$/, "")) + relParts[1];
+        path = path.replace(/(\/\.)+(\/|$)/g, "/").replace(/[^/]*\/\.\.(\/|$)/g, "");
+
+        return new URL(this.schema + "://" + this.host + this.port + path + relParts[2]);
+    },
+
+    sameOrigin: function(url)
+    {
+        function normalizePort(schema, port)
+        {
+            var portNo = port.slice(1);
+            return (schema === "https" && portNo == 443 || schema === "http" && portNo == 80) ? "" : port;
+        }
+
+        var other = new URL(url);
+
+        return this.schema === other.schema &&
+            this.host === other.host &&
+            normalizePort(this.schema, this.port) === normalizePort(other.schema, other.port);
+    }
+};
+
+function DOMCoreException(name, code)
+{
+    function formatError()
+    {
+        return "Error: " + this.message;
+    }
+
+    this.name = name;
+    this.message = name + ": DOM Exception " + code;
+    this.code = code;
+    this.toString = bind(formatError, this);
+}
+
+function bind(func, thisObject)
+{
+    var args = Array.prototype.slice.call(arguments, 2);
+    return function() { return func.apply(thisObject, args.concat(Array.prototype.slice.call(arguments, 0))); };
+}
+
+function noop()
+{
+}
+
+}
diff --git a/WebCore/inspector/front-end/InspectorBackendStub.js b/WebCore/inspector/front-end/InspectorBackendStub.js
index f5ee475..59e984b 100644
--- a/WebCore/inspector/front-end/InspectorBackendStub.js
+++ b/WebCore/inspector/front-end/InspectorBackendStub.js
@@ -264,6 +264,14 @@ WebInspector.InspectorBackendStub.prototype = {
 
     setInjectedScriptSource: function()
     {
+    },
+    
+    addScriptToEvaluateOnLoad: function()
+    {
+    },
+
+    removeAllScriptsToEvaluateOnLoad: function()
+    {
     }
 }
 
diff --git a/WebCore/inspector/front-end/WebKit.qrc b/WebCore/inspector/front-end/WebKit.qrc
index 581405d..8199fb6 100644
--- a/WebCore/inspector/front-end/WebKit.qrc
+++ b/WebCore/inspector/front-end/WebKit.qrc
@@ -32,6 +32,7 @@
     <file>EventListenersSidebarPane.js</file>
     <file>FontView.js</file>
     <file>ImageView.js</file>
+    <file>InjectedFakeWorker.js</file>
     <file>InjectedScript.js</file>
     <file>InjectedScriptAccess.js</file>
     <file>inspector.js</file>
diff --git a/WebCore/inspector/front-end/inspector.html b/WebCore/inspector/front-end/inspector.html
index 85633b5..e5295f2 100644
--- a/WebCore/inspector/front-end/inspector.html
+++ b/WebCore/inspector/front-end/inspector.html
@@ -85,6 +85,7 @@ THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
     <script type="text/javascript" src="SummaryBar.js"></script>
     <script type="text/javascript" src="ElementsPanel.js"></script>
     <script type="text/javascript" src="ResourcesPanel.js"></script>
+    <script type="text/javascript" src="InjectedFakeWorker.js"></script>
     <script type="text/javascript" src="ScriptsPanel.js"></script>
     <script type="text/javascript" src="StoragePanel.js"></script>
     <script type="text/javascript" src="ProfilesPanel.js"></script>

-- 
WebKit Debian packaging



More information about the Pkg-webkit-commits mailing list