[SCM] WebKit Debian packaging branch, webkit-1.3, updated. upstream/1.3.7-4207-g178b198
commit-queue at webkit.org
commit-queue at webkit.org
Sun Feb 20 23:42:34 UTC 2011
The following commit has been merged in the webkit-1.3 branch:
commit 8e2795bd484371d17e780449fb9e303229ebbbbe
Author: commit-queue at webkit.org <commit-queue at webkit.org@268f45cc-cd09-0410-ab3c-d52691b4dbfc>
Date: Mon Jan 24 12:58:32 2011 +0000
2011-01-24 Kimmo Kinnunen <kimmo.t.kinnunen at nokia.com>
Reviewed by Kenneth Rohde Christiansen.
[Qt] Remove CleanupHandler by passing file descriptors.
Deleting files in signal handler of UI process is not a good idea,
because the memory where filenames are stored might not be valid
after a crash.
To avoid the need of using signal handlers for cleanup,
change following:
1) Avoid passing filenames between processes, pass fds
2) When mmap'ing files, delete them immediately after
opening and mmap'ing them.
3) Pass sockets with fds during fork+exec instead of
passing them via the filesystem.
4) Use mmap'ed files for implementation of SharedMemory.
QSharedMemory does not support cleanup correctly.
Consquences:
- Move MappedMemory to SharedMemory, make UpdateChunk use this.
- Implement CoreIPC::Attachment using mmaped files.
- Send messages using datagram socket. This solution works
similiarly to Mach ports on Mac.
- Send big messages out-of-line and thus avoid increasing
the receive buffer.
- Remove MemoryMappedPool and rely on libc/kernel caching
of mmapped areas.
- Unmap memory areas after use.
- When UI process crashes, kill the web process using SIGKILL.
This is possible again because cleanup handler is not needed.
[WK2][Qt] Multiple problems with MemoryMappedPool
https://bugs.webkit.org/show_bug.cgi?id=51984
* Platform/CoreIPC/Attachment.cpp:
(CoreIPC::Attachment::Attachment):
* Platform/CoreIPC/Attachment.h:
(CoreIPC::Attachment::size):
(CoreIPC::Attachment::releaseFileDescriptor):
(CoreIPC::Attachment::fileDescriptor):
* Platform/CoreIPC/Connection.h:
* Platform/CoreIPC/qt/ConnectionQt.cpp:
(CoreIPC::MessageInfo::MessageInfo):
(CoreIPC::MessageInfo::setMessageBodyOOL):
(CoreIPC::MessageInfo::isMessageBodyOOL):
(CoreIPC::MessageInfo::bodySize):
(CoreIPC::MessageInfo::messageID):
(CoreIPC::MessageInfo::attachmentCount):
(CoreIPC::Connection::platformInitialize):
(CoreIPC::Connection::platformInvalidate):
(CoreIPC::SocketNotifierDisableGuard::SocketNotifierDisableGuard):
(CoreIPC::SocketNotifierDisableGuard::~SocketNotifierDisableGuard):
(CoreIPC::Connection::readyReadHandler):
(CoreIPC::Connection::open):
(CoreIPC::Connection::platformCanSendOutgoingMessages):
(CoreIPC::Connection::sendOutgoingMessage):
* Platform/SharedMemory.h:
* Platform/WorkQueue.h:
* Platform/qt/MappedMemoryPool.cpp: Removed.
* Platform/qt/MappedMemoryPool.h: Removed.
* Platform/qt/SharedMemoryQt.cpp:
(WebKit::SharedMemory::Handle::Handle):
(WebKit::SharedMemory::Handle::~Handle):
(WebKit::SharedMemory::Handle::isNull):
(WebKit::SharedMemory::Handle::encode):
(WebKit::SharedMemory::Handle::decode):
(WebKit::SharedMemory::Handle::releaseToAttachment):
(WebKit::SharedMemory::Handle::adoptFromAttachment):
(WebKit::SharedMemory::create):
(WebKit::accessModeMMap):
(WebKit::SharedMemory::~SharedMemory):
(WebKit::accessModeFile):
(WebKit::SharedMemory::createHandle):
* Platform/qt/WorkQueueQt.cpp:
(WorkQueue::registerSocketEventHandler):
* Shared/qt/UpdateChunk.cpp:
(WebKit::UpdateChunk::UpdateChunk):
(WebKit::UpdateChunk::~UpdateChunk):
(WebKit::UpdateChunk::encode):
(WebKit::UpdateChunk::decode):
(WebKit::UpdateChunk::createImage):
* Shared/qt/UpdateChunk.h:
* UIProcess/Launcher/ProcessLauncher.h:
* UIProcess/Launcher/qt/ProcessLauncherQt.cpp:
(WebKit::QtWebProcess::QtWebProcess):
(WebKit::QtWebProcess::setupChildProcess):
(WebKit::ProcessLauncher::launchProcess):
(WebKit::ProcessLauncher::platformInvalidate):
* UIProcess/Launcher/qt/ThreadLauncherQt.cpp:
(WebKit::webThreadBody):
(WebKit::ThreadLauncher::createWebThread):
* WebKit2.pro:
* WebProcess/qt/WebProcessMainQt.cpp:
(WebKit::WebProcessMainQt):
git-svn-id: http://svn.webkit.org/repository/webkit/trunk@76507 268f45cc-cd09-0410-ab3c-d52691b4dbfc
diff --git a/Source/WebKit2/ChangeLog b/Source/WebKit2/ChangeLog
index 331f0ab..a3a682c 100644
--- a/Source/WebKit2/ChangeLog
+++ b/Source/WebKit2/ChangeLog
@@ -1,3 +1,100 @@
+2011-01-24 Kimmo Kinnunen <kimmo.t.kinnunen at nokia.com>
+
+ Reviewed by Kenneth Rohde Christiansen.
+
+ [Qt] Remove CleanupHandler by passing file descriptors.
+
+ Deleting files in signal handler of UI process is not a good idea,
+ because the memory where filenames are stored might not be valid
+ after a crash.
+
+ To avoid the need of using signal handlers for cleanup,
+ change following:
+ 1) Avoid passing filenames between processes, pass fds
+ 2) When mmap'ing files, delete them immediately after
+ opening and mmap'ing them.
+ 3) Pass sockets with fds during fork+exec instead of
+ passing them via the filesystem.
+ 4) Use mmap'ed files for implementation of SharedMemory.
+ QSharedMemory does not support cleanup correctly.
+
+ Consquences:
+ - Move MappedMemory to SharedMemory, make UpdateChunk use this.
+ - Implement CoreIPC::Attachment using mmaped files.
+ - Send messages using datagram socket. This solution works
+ similiarly to Mach ports on Mac.
+ - Send big messages out-of-line and thus avoid increasing
+ the receive buffer.
+ - Remove MemoryMappedPool and rely on libc/kernel caching
+ of mmapped areas.
+ - Unmap memory areas after use.
+ - When UI process crashes, kill the web process using SIGKILL.
+ This is possible again because cleanup handler is not needed.
+
+ [WK2][Qt] Multiple problems with MemoryMappedPool
+ https://bugs.webkit.org/show_bug.cgi?id=51984
+
+ * Platform/CoreIPC/Attachment.cpp:
+ (CoreIPC::Attachment::Attachment):
+ * Platform/CoreIPC/Attachment.h:
+ (CoreIPC::Attachment::size):
+ (CoreIPC::Attachment::releaseFileDescriptor):
+ (CoreIPC::Attachment::fileDescriptor):
+ * Platform/CoreIPC/Connection.h:
+ * Platform/CoreIPC/qt/ConnectionQt.cpp:
+ (CoreIPC::MessageInfo::MessageInfo):
+ (CoreIPC::MessageInfo::setMessageBodyOOL):
+ (CoreIPC::MessageInfo::isMessageBodyOOL):
+ (CoreIPC::MessageInfo::bodySize):
+ (CoreIPC::MessageInfo::messageID):
+ (CoreIPC::MessageInfo::attachmentCount):
+ (CoreIPC::Connection::platformInitialize):
+ (CoreIPC::Connection::platformInvalidate):
+ (CoreIPC::SocketNotifierDisableGuard::SocketNotifierDisableGuard):
+ (CoreIPC::SocketNotifierDisableGuard::~SocketNotifierDisableGuard):
+ (CoreIPC::Connection::readyReadHandler):
+ (CoreIPC::Connection::open):
+ (CoreIPC::Connection::platformCanSendOutgoingMessages):
+ (CoreIPC::Connection::sendOutgoingMessage):
+ * Platform/SharedMemory.h:
+ * Platform/WorkQueue.h:
+ * Platform/qt/MappedMemoryPool.cpp: Removed.
+ * Platform/qt/MappedMemoryPool.h: Removed.
+ * Platform/qt/SharedMemoryQt.cpp:
+ (WebKit::SharedMemory::Handle::Handle):
+ (WebKit::SharedMemory::Handle::~Handle):
+ (WebKit::SharedMemory::Handle::isNull):
+ (WebKit::SharedMemory::Handle::encode):
+ (WebKit::SharedMemory::Handle::decode):
+ (WebKit::SharedMemory::Handle::releaseToAttachment):
+ (WebKit::SharedMemory::Handle::adoptFromAttachment):
+ (WebKit::SharedMemory::create):
+ (WebKit::accessModeMMap):
+ (WebKit::SharedMemory::~SharedMemory):
+ (WebKit::accessModeFile):
+ (WebKit::SharedMemory::createHandle):
+ * Platform/qt/WorkQueueQt.cpp:
+ (WorkQueue::registerSocketEventHandler):
+ * Shared/qt/UpdateChunk.cpp:
+ (WebKit::UpdateChunk::UpdateChunk):
+ (WebKit::UpdateChunk::~UpdateChunk):
+ (WebKit::UpdateChunk::encode):
+ (WebKit::UpdateChunk::decode):
+ (WebKit::UpdateChunk::createImage):
+ * Shared/qt/UpdateChunk.h:
+ * UIProcess/Launcher/ProcessLauncher.h:
+ * UIProcess/Launcher/qt/ProcessLauncherQt.cpp:
+ (WebKit::QtWebProcess::QtWebProcess):
+ (WebKit::QtWebProcess::setupChildProcess):
+ (WebKit::ProcessLauncher::launchProcess):
+ (WebKit::ProcessLauncher::platformInvalidate):
+ * UIProcess/Launcher/qt/ThreadLauncherQt.cpp:
+ (WebKit::webThreadBody):
+ (WebKit::ThreadLauncher::createWebThread):
+ * WebKit2.pro:
+ * WebProcess/qt/WebProcessMainQt.cpp:
+ (WebKit::WebProcessMainQt):
+
2011-01-24 Andras Becsi <abecsi at webkit.org>
Reviewed by Csaba Osztrogonác.
diff --git a/Source/WebKit2/Platform/CoreIPC/ArgumentDecoder.cpp b/Source/WebKit2/Platform/CoreIPC/ArgumentDecoder.cpp
index 336f72f..b7055f8 100644
--- a/Source/WebKit2/Platform/CoreIPC/ArgumentDecoder.cpp
+++ b/Source/WebKit2/Platform/CoreIPC/ArgumentDecoder.cpp
@@ -46,7 +46,13 @@ ArgumentDecoder::~ArgumentDecoder()
{
ASSERT(m_buffer);
fastFree(m_buffer);
+#if !PLATFORM(QT)
// FIXME: We need to dispose of the mach ports in cases of failure.
+#else
+ Deque<Attachment>::iterator end = m_attachments.end();
+ for (Deque<Attachment>::iterator it = m_attachments.begin(); it != end; ++it)
+ it->dispose();
+#endif
}
void ArgumentDecoder::initialize(const uint8_t* buffer, size_t bufferSize)
diff --git a/Source/WebKit2/Platform/CoreIPC/ArgumentEncoder.cpp b/Source/WebKit2/Platform/CoreIPC/ArgumentEncoder.cpp
index 1340c0a..85a7ca4 100644
--- a/Source/WebKit2/Platform/CoreIPC/ArgumentEncoder.cpp
+++ b/Source/WebKit2/Platform/CoreIPC/ArgumentEncoder.cpp
@@ -49,7 +49,12 @@ ArgumentEncoder::~ArgumentEncoder()
{
if (m_buffer)
fastFree(m_buffer);
+#if !PLATFORM(QT)
// FIXME: We need to dispose of the attachments in cases of failure.
+#else
+ for (int i = 0; i < m_attachments.size(); ++i)
+ m_attachments[i].dispose();
+#endif
}
static inline size_t roundUpToAlignment(size_t value, unsigned alignment)
diff --git a/Source/WebKit2/Platform/CoreIPC/Attachment.h b/Source/WebKit2/Platform/CoreIPC/Attachment.h
index 55a09c9..c057714 100644
--- a/Source/WebKit2/Platform/CoreIPC/Attachment.h
+++ b/Source/WebKit2/Platform/CoreIPC/Attachment.h
@@ -40,12 +40,16 @@ public:
#if PLATFORM(MAC)
MachPortType,
MachOOLMemoryType
+#elif PLATFORM(QT)
+ MappedMemory
#endif
};
#if PLATFORM(MAC)
Attachment(mach_port_name_t port, mach_msg_type_name_t disposition);
Attachment(void* address, mach_msg_size_t size, mach_msg_copy_options_t copyOptions, bool deallocate);
+#elif PLATFORM(QT)
+ Attachment(int fileDescriptor, size_t);
#endif
Type type() const { return m_type; }
@@ -62,6 +66,13 @@ public:
mach_msg_size_t size() const { ASSERT(m_type == MachOOLMemoryType); return m_oolMemory.size; }
mach_msg_copy_options_t copyOptions() const { ASSERT(m_type == MachOOLMemoryType); return m_oolMemory.copyOptions; }
bool deallocate() const { ASSERT(m_type == MachOOLMemoryType); return m_oolMemory.deallocate; }
+#elif PLATFORM(QT)
+ size_t size() const { return m_size; }
+
+ int releaseFileDescriptor() { int temp = m_fileDescriptor; m_fileDescriptor = -1; return temp; }
+ int fileDescriptor() const { return m_fileDescriptor; }
+
+ void dispose();
#endif
void encode(ArgumentEncoder*) const;
@@ -83,6 +94,9 @@ private:
bool deallocate;
} m_oolMemory;
};
+#elif PLATFORM(QT)
+ int m_fileDescriptor;
+ size_t m_size;
#endif
};
diff --git a/Source/WebKit2/Platform/CoreIPC/Connection.h b/Source/WebKit2/Platform/CoreIPC/Connection.h
index 1b009cf..58cb89c 100644
--- a/Source/WebKit2/Platform/CoreIPC/Connection.h
+++ b/Source/WebKit2/Platform/CoreIPC/Connection.h
@@ -44,9 +44,8 @@
#elif PLATFORM(WIN)
#include <string>
#elif PLATFORM(QT)
-#include <QString>
-class QLocalServer;
-class QLocalSocket;
+class QSocketNotifier;
+#include "PlatformProcessIdentifier.h"
#endif
class RunLoop;
@@ -98,7 +97,7 @@ public:
typedef HANDLE Identifier;
static bool createServerAndClientIdentifiers(Identifier& serverIdentifier, Identifier& clientIdentifier);
#elif PLATFORM(QT)
- typedef const QString Identifier;
+ typedef int Identifier;
#elif PLATFORM(GTK)
typedef int Identifier;
#endif
@@ -109,6 +108,8 @@ public:
#if PLATFORM(MAC)
void setShouldCloseConnectionOnMachExceptions();
+#elif PLATFORM(QT)
+ void setShouldCloseConnectionOnProcessTermination(WebKit::PlatformProcessIdentifier);
#endif
bool open();
@@ -285,8 +286,8 @@ private:
Vector<uint8_t> m_readBuffer;
size_t m_currentMessageSize;
- QLocalSocket* m_socket;
- QString m_serverName;
+ QSocketNotifier* m_socketNotifier;
+ int m_socketDescriptor;
#elif PLATFORM(GTK)
void readEventHandler();
void processCompletedMessage();
diff --git a/Source/WebKit2/Platform/CoreIPC/qt/AttachmentQt.cpp b/Source/WebKit2/Platform/CoreIPC/qt/AttachmentQt.cpp
new file mode 100644
index 0000000..66aa7d9
--- /dev/null
+++ b/Source/WebKit2/Platform/CoreIPC/qt/AttachmentQt.cpp
@@ -0,0 +1,51 @@
+/*
+ * Copyright (C) 2010 Apple Inc. All rights reserved.
+ * Copyright (C) 2010 Nokia Corporation and/or its subsidiary(-ies)
+ *
+ * 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 "Attachment.h"
+#if PLATFORM(QT)
+#include <unistd.h>
+#include <errno.h>
+#endif
+
+
+namespace CoreIPC {
+
+Attachment::Attachment(int fileDescriptor, size_t size)
+ : m_type(MappedMemory)
+ , m_fileDescriptor(fileDescriptor)
+ , m_size(size)
+{
+ ASSERT(m_fileDescriptor);
+ ASSERT(m_size);
+}
+
+void Attachment::dispose()
+{
+ if (m_fileDescriptor != -1)
+ while (close(m_fileDescriptor) == -1 && (errno == EINTR)) { }
+}
+
+} // namespace CoreIPC
diff --git a/Source/WebKit2/Platform/CoreIPC/qt/ConnectionQt.cpp b/Source/WebKit2/Platform/CoreIPC/qt/ConnectionQt.cpp
index c0736b8..5a90568 100644
--- a/Source/WebKit2/Platform/CoreIPC/qt/ConnectionQt.cpp
+++ b/Source/WebKit2/Platform/CoreIPC/qt/ConnectionQt.cpp
@@ -29,114 +29,331 @@
#include "ArgumentEncoder.h"
#include "ProcessLauncher.h"
#include "WorkItem.h"
+#include "SharedMemory.h"
+#include "WebProcessProxy.h"
#include <QApplication>
-#include <QLocalServer>
-#include <QLocalSocket>
+#include <QSocketNotifier>
+#include <sys/socket.h>
+#include <unistd.h>
+#include <errno.h>
+#include <fcntl.h>
+#include <wtf/Assertions.h>
using namespace std;
namespace CoreIPC {
-// This is what other ports use...
static const size_t messageMaxSize = 4096;
+static const size_t attachmentMaxAmount = 255;
+
+enum {
+ MessageBodyIsOOL = 1 << 31
+};
+
+class MessageInfo {
+public:
+ MessageInfo() { }
+
+ MessageInfo(MessageID messageID, size_t bodySize, size_t initialAttachmentCount)
+ : m_messageID(messageID.toInt())
+ , m_bodySize(bodySize)
+ , m_attachmentCount(initialAttachmentCount)
+ {
+ ASSERT(!(m_messageID & MessageBodyIsOOL));
+ }
+
+ void setMessageBodyOOL()
+ {
+ ASSERT(!isMessageBodyOOL());
+
+ m_messageID |= MessageBodyIsOOL;
+ m_attachmentCount++;
+ }
+
+ bool isMessageBodyOOL() const { return m_messageID & MessageBodyIsOOL; }
+
+ size_t bodySize() const { return m_bodySize; }
+
+ MessageID messageID() const { return MessageID::fromInt(m_messageID & ~MessageBodyIsOOL); }
+
+ size_t attachmentCount() const { return m_attachmentCount; }
+
+private:
+ uint32_t m_messageID;
+ size_t m_bodySize;
+ size_t m_attachmentCount;
+};
void Connection::platformInitialize(Identifier identifier)
{
- m_serverName = identifier;
- m_socket = 0;
+ m_socketDescriptor = identifier;
+ m_socketNotifier = 0;
m_readBuffer.resize(messageMaxSize);
m_currentMessageSize = 0;
}
void Connection::platformInvalidate()
{
- m_socket->disconnect();
- if (!m_isServer)
- m_socket->deleteLater();
- m_socket = 0;
+ if (m_socketDescriptor != -1)
+ while (close(m_socketDescriptor) == -1 && errno == EINTR) { }
+
+ if (!m_isConnected)
+ return;
+
+ delete m_socketNotifier;
+ m_socketNotifier = 0;
+ m_socketDescriptor = -1;
+ m_isConnected = false;
}
+class SocketNotifierResourceGuard {
+public:
+ SocketNotifierResourceGuard(QSocketNotifier* socketNotifier)
+ : m_socketNotifier(socketNotifier)
+ {
+ m_socketNotifier->setEnabled(false);
+ }
+
+ ~SocketNotifierResourceGuard()
+ {
+ m_socketNotifier->setEnabled(true);
+ }
+
+private:
+ QSocketNotifier* const m_socketNotifier;
+};
+
+template<class T, class iterator>
+class AttachmentResourceGuard {
+public:
+ AttachmentResourceGuard(T& attachments)
+ : m_attachments(attachments)
+ {
+ }
+ ~AttachmentResourceGuard()
+ {
+ iterator end = m_attachments.end();
+ for (iterator i = m_attachments.begin(); i != end; ++i)
+ i->dispose();
+ }
+private:
+ T& m_attachments;
+};
+
void Connection::readyReadHandler()
{
- while (m_socket->bytesAvailable()) {
- if (!m_currentMessageSize) {
- size_t numberOfBytesRead = m_socket->read(reinterpret_cast<char*>(m_readBuffer.data()), sizeof(size_t));
- ASSERT_UNUSED(numberOfBytesRead, numberOfBytesRead);
- m_currentMessageSize = *reinterpret_cast<size_t*>(m_readBuffer.data());
- }
+ Deque<Attachment> attachments;
+ SocketNotifierResourceGuard socketNotifierEnabler(m_socketNotifier);
+ AttachmentResourceGuard<Deque<Attachment>, Deque<Attachment>::iterator> attachementDisposer(attachments);
+
+ char attachmentDescriptorBuffer[CMSG_SPACE(sizeof(int) * (attachmentMaxAmount))];
+ struct msghdr message;
+ memset(&message, 0, sizeof(message));
+
+ struct iovec iov[1];
+ memset(&iov, 0, sizeof(iov));
+
+ message.msg_control = attachmentDescriptorBuffer;
+ message.msg_controllen = CMSG_SPACE(sizeof(int) * (attachmentMaxAmount));
+
+ iov[0].iov_base = m_readBuffer.data();
+ iov[0].iov_len = m_readBuffer.size();
+
+ message.msg_iov = iov;
+ message.msg_iovlen = 1;
+
- if (m_socket->bytesAvailable() < m_currentMessageSize)
+ int messageLength = 0;
+ while ((messageLength = recvmsg(m_socketDescriptor, &message, MSG_CMSG_CLOEXEC)) == -1) {
+ if (errno != EINTR)
return;
+ }
+
+ struct cmsghdr* controlMessage = CMSG_FIRSTHDR(&message);
+
+ MessageInfo messageInfo;
+ unsigned char* messageData = m_readBuffer.data();
+
+ memcpy(&messageInfo, messageData, sizeof(messageInfo));
+ ASSERT(messageLength == sizeof(messageInfo) + messageInfo.attachmentCount() * sizeof(size_t) + (messageInfo.isMessageBodyOOL() ? 0 : messageInfo.bodySize()));
+
+ messageData += sizeof(messageInfo);
+
+ RefPtr<WebKit::SharedMemory> oolMessageBody;
+
+ if (messageInfo.attachmentCount()) {
+ if (controlMessage && controlMessage->cmsg_level == SOL_SOCKET && controlMessage->cmsg_type == SCM_RIGHTS) {
+ size_t attachmentSizes[messageInfo.attachmentCount()];
+ memcpy(attachmentSizes, messageData, sizeof(attachmentSizes));
+
+ messageData += sizeof(attachmentSizes);
+
+ int fileDescriptors[messageInfo.attachmentCount()];
+ memcpy(fileDescriptors, CMSG_DATA(controlMessage), sizeof(fileDescriptors));
- if (m_readBuffer.size() < m_currentMessageSize)
- m_readBuffer.grow(m_currentMessageSize);
+ int attachmentCount = messageInfo.attachmentCount();
- size_t numberOfBytesRead = m_socket->read(reinterpret_cast<char*>(m_readBuffer.data()), m_currentMessageSize);
- ASSERT_UNUSED(numberOfBytesRead, numberOfBytesRead);
+ if (messageInfo.isMessageBodyOOL())
+ attachmentCount--;
- // The messageID is encoded at the end of the buffer.
- size_t realBufferSize = m_currentMessageSize - sizeof(uint32_t);
- uint32_t messageID = *reinterpret_cast<uint32_t*>(m_readBuffer.data() + realBufferSize);
+ for (int i = 0; i < attachmentCount; ++i)
+ attachments.append(Attachment(fileDescriptors[i], attachmentSizes[i]));
- processIncomingMessage(MessageID::fromInt(messageID), adoptPtr(new ArgumentDecoder(m_readBuffer.data(), realBufferSize)));
+ if (messageInfo.isMessageBodyOOL()) {
+ ASSERT(messageInfo.bodySize());
- m_currentMessageSize = 0;
+ WebKit::SharedMemory::Handle handle;
+ handle.adoptFromAttachment(fileDescriptors[attachmentCount], attachmentSizes[attachmentCount]);
+ if (handle.isNull()) {
+ ASSERT_NOT_REACHED();
+ return;
+ }
+
+ oolMessageBody = WebKit::SharedMemory::create(handle, WebKit::SharedMemory::ReadOnly);
+ if (!oolMessageBody) {
+ ASSERT_NOT_REACHED();
+ return;
+ }
+ }
+
+ controlMessage = CMSG_NXTHDR(&message, controlMessage);
+ } else {
+ ASSERT_NOT_REACHED();
+ return;
+ }
}
+
+ ASSERT(attachments.size() == messageInfo.isMessageBodyOOL() ? messageInfo.attachmentCount() - 1 : messageInfo.attachmentCount());
+
+ unsigned char* messageBody = messageData;
+
+ if (messageInfo.isMessageBodyOOL())
+ messageBody = reinterpret_cast<unsigned char*>(oolMessageBody->data());
+
+ ArgumentDecoder* argumentDecoder;
+ if (attachments.isEmpty())
+ argumentDecoder = new ArgumentDecoder(messageBody, messageInfo.bodySize());
+ else
+ argumentDecoder = new ArgumentDecoder(messageBody, messageInfo.bodySize(), attachments);
+
+ processIncomingMessage(messageInfo.messageID(), adoptPtr(argumentDecoder));
+
+ ASSERT(!controlMessage);
}
bool Connection::open()
{
- ASSERT(!m_socket);
-
- if (m_isServer) {
- m_socket = WebKit::ProcessLauncher::takePendingConnection();
- m_isConnected = m_socket;
- if (m_isConnected) {
- m_connectionQueue.moveSocketToWorkThread(m_socket);
- m_connectionQueue.connectSignal(m_socket, SIGNAL(readyRead()), WorkItem::create(this, &Connection::readyReadHandler));
+ ASSERT(!m_socketNotifier);
+ int flags = fcntl(m_socketDescriptor, F_GETFL, 0);
+ while (fcntl(m_socketDescriptor, F_SETFL, flags | O_NONBLOCK) == -1) {
+ if (errno != EINTR) {
+ ASSERT_NOT_REACHED();
+ return false;
}
- } else {
- m_socket = new QLocalSocket();
- m_socket->connectToServer(m_serverName);
- m_connectionQueue.moveSocketToWorkThread(m_socket);
- m_connectionQueue.connectSignal(m_socket, SIGNAL(readyRead()), WorkItem::create(this, &Connection::readyReadHandler));
- m_connectionQueue.connectSignal(m_socket, SIGNAL(disconnected()), WorkItem::create(this, &Connection::connectionDidClose));
- m_isConnected = m_socket->waitForConnected();
}
- return m_isConnected;
+
+ m_isConnected = true;
+ m_socketNotifier = m_connectionQueue.registerSocketEventHandler(m_socketDescriptor, QSocketNotifier::Read, WorkItem::create(this, &Connection::readyReadHandler));
+
+ // Schedule a call to readyReadHandler. Data may have arrived before installation of the signal
+ // handler.
+ m_connectionQueue.scheduleWork(WorkItem::create(this, &Connection::readyReadHandler));
+
+ return true;
}
bool Connection::platformCanSendOutgoingMessages() const
{
- return m_socket;
+ return m_socketNotifier;
}
bool Connection::sendOutgoingMessage(MessageID messageID, PassOwnPtr<ArgumentEncoder> arguments)
{
- ASSERT(m_socket);
-
- // We put the message ID last.
- arguments->encodeUInt32(messageID.toInt());
+ ASSERT(m_socketNotifier);
+ COMPILE_ASSERT(sizeof(MessageInfo) + attachmentMaxAmount * sizeof(size_t) <= messageMaxSize, AttachmentsFitToMessageInline);
- size_t bufferSize = arguments->bufferSize();
+ Vector<Attachment> attachments = arguments->releaseAttachments();
+ AttachmentResourceGuard<Vector<Attachment>, Vector<Attachment>::iterator> attachementDisposer(attachments);
- // Write message size first
- // FIXME: Should just do a single write.
- qint64 bytesWrittenForSize = m_socket->write(reinterpret_cast<char*>(&bufferSize), sizeof(bufferSize));
- if (bytesWrittenForSize != sizeof(bufferSize)) {
- connectionDidClose();
+ if (attachments.size() > (attachmentMaxAmount - 1)) {
+ ASSERT_NOT_REACHED();
return false;
}
- qint64 bytesWrittenForBuffer = m_socket->write(reinterpret_cast<char*>(arguments->buffer()), arguments->bufferSize());
- if (bytesWrittenForBuffer != arguments->bufferSize()) {
- connectionDidClose();
- return false;
+ MessageInfo messageInfo(messageID, arguments->bufferSize(), attachments.size());
+ size_t messageSizeWithBodyInline = sizeof(messageInfo) + (attachments.size() * sizeof(size_t)) + arguments->bufferSize();
+ if (messageSizeWithBodyInline > messageMaxSize && arguments->bufferSize()) {
+ RefPtr<WebKit::SharedMemory> oolMessageBody = WebKit::SharedMemory::create(arguments->bufferSize());
+ if (!oolMessageBody)
+ return false;
+
+ WebKit::SharedMemory::Handle handle;
+ if (!oolMessageBody->createHandle(handle, WebKit::SharedMemory::ReadOnly))
+ return false;
+
+ messageInfo.setMessageBodyOOL();
+
+ memcpy(oolMessageBody->data(), arguments->buffer(), arguments->bufferSize());
+
+ attachments.append(handle.releaseToAttachment());
}
- m_socket->flush();
+ struct msghdr message;
+ memset(&message, 0, sizeof(message));
+
+ struct iovec iov[3];
+ memset(&iov, 0, sizeof(iov));
+
+ message.msg_iov = iov;
+ int iovLength = 1;
+
+ iov[0].iov_base = reinterpret_cast<void*>(&messageInfo);
+ iov[0].iov_len = sizeof(messageInfo);
+
+ char attachmentFDBuffer[CMSG_SPACE(sizeof(int) * (attachments.size()))];
+ size_t attachmentSizes[attachments.size()];
+
+ if (!attachments.isEmpty()) {
+ message.msg_control = attachmentFDBuffer;
+ message.msg_controllen = sizeof(attachmentFDBuffer);
+
+ struct cmsghdr* cmsg = CMSG_FIRSTHDR(&message);
+ cmsg->cmsg_level = SOL_SOCKET;
+ cmsg->cmsg_type = SCM_RIGHTS;
+ cmsg->cmsg_len = CMSG_LEN(sizeof(int) * attachments.size());
+
+ int* fdptr = reinterpret_cast<int*>(CMSG_DATA(cmsg));
+ for (int i = 0; i < attachments.size(); ++i) {
+ attachmentSizes[i] = attachments[i].size();
+ fdptr[i] = attachments[i].fileDescriptor();
+ }
+
+ message.msg_controllen = cmsg->cmsg_len;
+ iov[iovLength].iov_base = attachmentSizes;
+ iov[iovLength].iov_len = sizeof(attachmentSizes);
+ ++iovLength;
+ }
+
+ if (!messageInfo.isMessageBodyOOL() && arguments->bufferSize()) {
+ iov[iovLength].iov_base = reinterpret_cast<void*>(arguments->buffer());
+ iov[iovLength].iov_len = arguments->bufferSize();
+ ++iovLength;
+ }
+
+ message.msg_iovlen = iovLength;
+
+ int bytesSent = 0;
+ while ((bytesSent = sendmsg(m_socketDescriptor, &message, 0)) == -1) {
+ if (errno != EINTR)
+ return false;
+ }
return true;
}
+void Connection::setShouldCloseConnectionOnProcessTermination(WebKit::PlatformProcessIdentifier process)
+{
+ m_connectionQueue.scheduleWorkOnTermination(process, WorkItem::create(this, &Connection::connectionDidClose));
+}
+
} // namespace CoreIPC
diff --git a/Source/WebKit2/Platform/SharedMemory.h b/Source/WebKit2/Platform/SharedMemory.h
index 9854132..fd1d60c 100644
--- a/Source/WebKit2/Platform/SharedMemory.h
+++ b/Source/WebKit2/Platform/SharedMemory.h
@@ -31,10 +31,7 @@
#include <wtf/RefCounted.h>
#if PLATFORM(QT)
-#include <QtGlobal>
-QT_BEGIN_NAMESPACE
-class QSharedMemory;
-QT_END_NAMESPACE
+#include "Attachment.h"
#include <wtf/text/WTFString.h>
#endif
@@ -63,6 +60,10 @@ public:
void encode(CoreIPC::ArgumentEncoder*) const;
static bool decode(CoreIPC::ArgumentDecoder*, Handle&);
+#if PLATFORM(QT)
+ CoreIPC::Attachment releaseToAttachment() const;
+ void adoptFromAttachment(int fileDescriptor, size_t);
+#endif
private:
friend class SharedMemory;
#if PLATFORM(MAC)
@@ -70,7 +71,7 @@ public:
#elif PLATFORM(WIN)
mutable HANDLE m_handle;
#elif PLATFORM(QT)
- mutable String m_key;
+ mutable int m_fileDescriptor;
#endif
size_t m_size;
};
@@ -97,7 +98,7 @@ private:
#if PLATFORM(WIN)
HANDLE m_handle;
#elif PLATFORM(QT)
- QSharedMemory* m_impl;
+ int m_fileDescriptor;
#endif
};
diff --git a/Source/WebKit2/Platform/WorkQueue.h b/Source/WebKit2/Platform/WorkQueue.h
index 78fa8b7..bcaae0e 100644
--- a/Source/WebKit2/Platform/WorkQueue.h
+++ b/Source/WebKit2/Platform/WorkQueue.h
@@ -41,7 +41,8 @@
#include <wtf/Vector.h>
#if PLATFORM(QT)
-class QLocalSocket;
+#include <QSocketNotifier>
+#include "PlatformProcessIdentifier.h"
class QObject;
class QThread;
#elif PLATFORM(GTK)
@@ -79,10 +80,8 @@ public:
void registerHandle(HANDLE, PassOwnPtr<WorkItem>);
void unregisterAndCloseHandle(HANDLE);
#elif PLATFORM(QT)
- void connectSignal(QObject*, const char* signal, PassOwnPtr<WorkItem>);
- void disconnectSignal(QObject*, const char* signal);
-
- void moveSocketToWorkThread(QLocalSocket*);
+ QSocketNotifier* registerSocketEventHandler(int, QSocketNotifier::Type, PassOwnPtr<WorkItem>);
+ void scheduleWorkOnTermination(WebKit::PlatformProcessIdentifier, PassOwnPtr<WorkItem>);
#elif PLATFORM(GTK)
void registerEventSourceHandler(int, int, PassOwnPtr<WorkItem>);
void unregisterEventSourceHandler(int);
diff --git a/Source/WebKit2/Platform/qt/MappedMemoryPool.cpp b/Source/WebKit2/Platform/qt/MappedMemoryPool.cpp
deleted file mode 100644
index d36d82b..0000000
--- a/Source/WebKit2/Platform/qt/MappedMemoryPool.cpp
+++ /dev/null
@@ -1,114 +0,0 @@
-/*
- * Copyright (C) 2010 University of Szeged
- * Copyright (C) 2010 Nokia Corporation and/or its subsidiary(-ies)
- * 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 UNIVERSITY OF SZEGED ``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 UNIVERSITY OF SZEGED 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.
- */
-
-#include "MappedMemoryPool.h"
-
-#include "CleanupHandler.h"
-#include "StdLibExtras.h"
-#include <QDir>
-#include <QIODevice>
-#include <QTemporaryFile>
-
-namespace WebKit {
-
-MappedMemoryPool* MappedMemoryPool::theInstance = 0;
-
-MappedMemoryPool* MappedMemoryPool::instance()
-{
- if (!theInstance) {
- theInstance = new MappedMemoryPool;
-
- // Do not leave mapping files on the disk.
- CleanupHandler::instance()->markForCleanup(theInstance);
- }
-
- return theInstance;
-}
-
-MappedMemoryPool::~MappedMemoryPool()
-{
- CleanupHandler::instance()->unmark(theInstance);
-
- for (unsigned n = 0; n < m_pool.size(); ++n) {
- MappedMemory& current = m_pool.at(n);
- if (!current.file)
- continue;
- current.file->remove();
- delete current.file;
- }
- m_pool.clear();
-}
-
-MappedMemory* MappedMemoryPool::mapMemory(size_t size)
-{
- for (unsigned n = 0; n < m_pool.size(); ++n) {
- MappedMemory& current = m_pool.at(n);
- if (current.dataSize >= size && current.isFree()) {
- current.markUsed();
- return ¤t;
- }
- }
-
- MappedMemory newMap;
- newMap.dataSize = size;
- newMap.file = new QTemporaryFile(QDir::tempPath() + "/WebKit2UpdateChunk");
- newMap.file->open(QIODevice::ReadWrite);
- newMap.fileName = newMap.file->fileName();
- newMap.file->resize(newMap.mapSize());
- newMap.mappedBytes = newMap.file->map(0, newMap.mapSize());
- newMap.file->close();
- newMap.markUsed();
- m_pool.append(newMap);
- return &m_pool.last();
-}
-
-MappedMemory* MappedMemoryPool::mapFile(QString fileName, size_t size)
-{
- for (unsigned n = 0; n < m_pool.size(); ++n) {
- MappedMemory& current = m_pool.at(n);
- if (current.fileName == fileName) {
- ASSERT(!current.isFree());
- return ¤t;
- }
- }
-
- MappedMemory newMap;
- newMap.file = new QFile(fileName);
- newMap.fileName = fileName;
- newMap.dataSize = size;
- ASSERT(newMap.file->exists());
- ASSERT(newMap.file->size() >= newMap.mapSize());
- newMap.file->open(QIODevice::ReadWrite);
- newMap.mappedBytes = newMap.file->map(0, newMap.mapSize());
- ASSERT(newMap.mappedBytes);
- ASSERT(!newMap.isFree());
- newMap.file->close();
- m_pool.append(newMap);
- return &m_pool.last();
-}
-
-} // namespace WebKit
diff --git a/Source/WebKit2/Platform/qt/MappedMemoryPool.h b/Source/WebKit2/Platform/qt/MappedMemoryPool.h
deleted file mode 100644
index 8d6af8c..0000000
--- a/Source/WebKit2/Platform/qt/MappedMemoryPool.h
+++ /dev/null
@@ -1,109 +0,0 @@
-/*
- * Copyright (C) 2010 Apple Inc. All rights reserved.
- * Copyright (C) 2010 Nokia Corporation and/or its subsidiary(-ies)
- * Copyright (C) 2010 University of Szeged
- *
- * 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 MappedMemoryPool_h
-#define MappedMemoryPool_h
-
-#include <QFile>
-#include <QObject>
-#include <wtf/StdLibExtras.h>
-#include <wtf/Vector.h>
-
-namespace WebKit {
-
-class MappedMemoryPool;
-
-struct MappedMemory {
-
- QString mappedFileName() const
- {
- ASSERT(file);
- ASSERT(mappedBytes);
- return fileName;
- }
-
- void markFree()
- {
- ASSERT(mappedBytes);
- dataPtr->isFree = true;
- }
-
- uchar* data() const
- {
- ASSERT(mappedBytes);
- return dataPtr->bytes;
- }
-
-private:
- friend class MappedMemoryPool;
-
- MappedMemory()
- : file(0)
- , mappedBytes(0)
- , dataSize(0)
- {
- }
-
- void markUsed() { dataPtr->isFree = false; }
-
- size_t mapSize() const { return dataSize + sizeof(Data); }
- bool isFree() const { return dataPtr->isFree; }
-
- struct Data {
- uint32_t isFree; // keep bytes aligned
- uchar bytes[];
- };
-
- QFile* file;
- QString fileName;
- union {
- uchar* mappedBytes;
- Data* dataPtr;
- };
- size_t dataSize;
-};
-
-class MappedMemoryPool : QObject {
- Q_OBJECT
-public:
- static MappedMemoryPool* instance();
-
- MappedMemory* mapMemory(size_t size);
- MappedMemory* mapFile(QString fileName, size_t size);
-
-private:
- MappedMemoryPool() { }
- ~MappedMemoryPool();
-
- static MappedMemoryPool* theInstance;
-
- Vector<MappedMemory> m_pool;
-};
-
-} // namespace WebKit
-
-#endif // MappedMemoryPool_h
diff --git a/Source/WebKit2/Platform/qt/SharedMemoryQt.cpp b/Source/WebKit2/Platform/qt/SharedMemoryQt.cpp
index f5fecfc..2e6141d 100644
--- a/Source/WebKit2/Platform/qt/SharedMemoryQt.cpp
+++ b/Source/WebKit2/Platform/qt/SharedMemoryQt.cpp
@@ -29,139 +29,181 @@
#include "ArgumentDecoder.h"
#include "ArgumentEncoder.h"
-#include "CleanupHandler.h"
#include "WebCoreArgumentCoders.h"
+#include <QDir>
+#include <errno.h>
+#include <fcntl.h>
+#include <stdlib.h>
+#include <sys/mman.h>
+#include <sys/stat.h>
+#include <sys/types.h>
#include <unistd.h>
-#include <QCoreApplication>
-#include <QLatin1String>
-#include <QSharedMemory>
-#include <QString>
-#include <QUuid>
#include <wtf/Assertions.h>
#include <wtf/CurrentTime.h>
namespace WebKit {
SharedMemory::Handle::Handle()
- : m_key()
+ : m_fileDescriptor(-1)
, m_size(0)
{
}
SharedMemory::Handle::~Handle()
{
+ if (!isNull())
+ while (close(m_fileDescriptor) == -1 && errno == EINTR) { }
}
bool SharedMemory::Handle::isNull() const
{
- return m_key.isNull();
+ return m_fileDescriptor == -1;
}
void SharedMemory::Handle::encode(CoreIPC::ArgumentEncoder* encoder) const
{
- encoder->encodeUInt64(m_size);
- encoder->encode(m_key);
- m_key = String();
+ ASSERT(!isNull());
+
+ encoder->encode(releaseToAttachment());
}
bool SharedMemory::Handle::decode(CoreIPC::ArgumentDecoder* decoder, Handle& handle)
{
ASSERT_ARG(handle, !handle.m_size);
- ASSERT_ARG(handle, handle.m_key.isNull());
+ ASSERT_ARG(handle, handle.isNull());
- uint64_t size;
- if (!decoder->decodeUInt64(size))
+ CoreIPC::Attachment attachment;
+ if (!decoder->decode(attachment))
return false;
- String key;
- if (!decoder->decode(key))
- return false;
+ handle.adoptFromAttachment(attachment.releaseFileDescriptor(), attachment.size());
+ return true;
+}
- handle.m_size = size;
- handle.m_key = key;
+CoreIPC::Attachment SharedMemory::Handle::releaseToAttachment() const
+{
+ ASSERT(!isNull());
- return true;
+ int temp = m_fileDescriptor;
+ m_fileDescriptor = -1;
+ return CoreIPC::Attachment(temp, m_size);
}
-static QString createUniqueKey()
+void SharedMemory::Handle::adoptFromAttachment(int fileDescriptor, size_t size)
{
- return QLatin1String("QWKSharedMemoryKey") + QUuid::createUuid().toString();
+ ASSERT(!m_size);
+ ASSERT(isNull());
+
+ m_fileDescriptor = fileDescriptor;
+ m_size = size;
}
PassRefPtr<SharedMemory> SharedMemory::create(size_t size)
{
- RefPtr<SharedMemory> sharedMemory(adoptRef(new SharedMemory));
- QSharedMemory* impl = new QSharedMemory(createUniqueKey());
- bool created = impl->create(size);
- ASSERT_UNUSED(created, created);
+ QString tempName = QDir::temp().filePath("qwkshm.XXXXXX");
+ QByteArray tempNameCSTR = tempName.toLocal8Bit();
+ char* tempNameC = tempNameCSTR.data();
+
+ int fileDescriptor;
+ while ((fileDescriptor = mkostemp(tempNameC, O_CREAT | O_CLOEXEC | O_RDWR)) == -1) {
+ if (errno != EINTR)
+ return 0;
+ }
- sharedMemory->m_impl = impl;
- sharedMemory->m_size = size;
- sharedMemory->m_data = impl->data();
+ while (ftruncate(fileDescriptor, size) == -1) {
+ if (errno != EINTR) {
+ while (close(fileDescriptor) == -1 && errno == EINTR) { }
+ unlink(tempNameC);
+ return 0;
+ }
+ }
+
+ void* data = mmap(0, size, PROT_READ | PROT_WRITE, MAP_SHARED, fileDescriptor, 0);
+ if (data == MAP_FAILED) {
+ while (close(fileDescriptor) == -1 && errno == EINTR) { }
+ unlink(tempNameC);
+ return 0;
+ }
- // Do not leave the shared memory segment behind.
- CleanupHandler::instance()->markForCleanup(impl);
+ unlink(tempNameC);
- return sharedMemory.release();
+ RefPtr<SharedMemory> instance = adoptRef(new SharedMemory());
+ instance->m_data = data;
+ instance->m_fileDescriptor = fileDescriptor;
+ instance->m_size = size;
+ return instance.release();
}
-static inline QSharedMemory::AccessMode accessMode(SharedMemory::Protection protection)
+static inline int accessModeMMap(SharedMemory::Protection protection)
{
switch (protection) {
case SharedMemory::ReadOnly:
- return QSharedMemory::ReadOnly;
+ return PROT_READ;
case SharedMemory::ReadWrite:
- return QSharedMemory::ReadWrite;
+ return PROT_READ | PROT_WRITE;
}
ASSERT_NOT_REACHED();
- return QSharedMemory::ReadWrite;
+ return PROT_READ | PROT_WRITE;
}
PassRefPtr<SharedMemory> SharedMemory::create(const Handle& handle, Protection protection)
{
- if (handle.isNull())
- return 0;
+ ASSERT(!handle.isNull());
- QSharedMemory* impl = new QSharedMemory(QString(handle.m_key));
- bool attached = impl->attach(accessMode(protection));
- if (!attached) {
- delete impl;
+ void* data = mmap(0, handle.m_size, accessModeMMap(protection), MAP_SHARED, handle.m_fileDescriptor, 0);
+ if (data == MAP_FAILED)
return 0;
- }
-
- RefPtr<SharedMemory> sharedMemory(adoptRef(new SharedMemory));
- sharedMemory->m_impl = impl;
- ASSERT(handle.m_size == impl->size());
- sharedMemory->m_size = handle.m_size;
- sharedMemory->m_data = impl->data();
- // Do not leave the shared memory segment behind.
- CleanupHandler::instance()->markForCleanup(impl);
-
- return sharedMemory.release();
+ RefPtr<SharedMemory> instance = adoptRef(new SharedMemory());
+ instance->m_data = data;
+ instance->m_fileDescriptor = handle.m_fileDescriptor;
+ instance->m_size = handle.m_size;
+ handle.m_fileDescriptor = -1;
+ return instance;
}
SharedMemory::~SharedMemory()
{
- if (CleanupHandler::instance()->hasStartedDeleting())
- return;
+ munmap(m_data, m_size);
+ while (close(m_fileDescriptor) == -1 && errno == EINTR) { }
+}
- CleanupHandler::instance()->unmark(m_impl);
- delete m_impl;
+static inline int accessModeFile(SharedMemory::Protection protection)
+{
+ switch (protection) {
+ case SharedMemory::ReadOnly:
+ return O_RDONLY;
+ case SharedMemory::ReadWrite:
+ return O_RDWR;
+ }
+
+ ASSERT_NOT_REACHED();
+ return O_RDWR;
}
bool SharedMemory::createHandle(Handle& handle, Protection protection)
{
- ASSERT_ARG(handle, handle.m_key.isNull());
ASSERT_ARG(handle, !handle.m_size);
+ ASSERT_ARG(handle, handle.isNull());
+
+ int duplicatedHandle;
+ while ((duplicatedHandle = dup(m_fileDescriptor)) == -1) {
+ if (errno != EINTR) {
+ ASSERT_NOT_REACHED();
+ return false;
+ }
+ }
- QString key = m_impl->key();
- if (key.isNull())
- return false;
- handle.m_key = String(key);
+ while ((fcntl(duplicatedHandle, F_SETFD, O_CLOEXEC | accessModeFile(protection)) == -1)) {
+ if (errno != EINTR) {
+ ASSERT_NOT_REACHED();
+ while (close(duplicatedHandle) == -1 && errno == EINTR) { }
+ return false;
+ }
+ }
+ handle.m_fileDescriptor = duplicatedHandle;
handle.m_size = m_size;
-
return true;
}
diff --git a/Source/WebKit2/Platform/qt/WorkQueueQt.cpp b/Source/WebKit2/Platform/qt/WorkQueueQt.cpp
index 271984f..99ce96e 100644
--- a/Source/WebKit2/Platform/qt/WorkQueueQt.cpp
+++ b/Source/WebKit2/Platform/qt/WorkQueueQt.cpp
@@ -29,6 +29,7 @@
#include <QLocalSocket>
#include <QObject>
#include <QThread>
+#include <QProcess>
#include <wtf/Threading.h>
#include "NotImplemented.h"
@@ -75,32 +76,17 @@ public:
WorkItem* m_workItem;
};
-void WorkQueue::connectSignal(QObject* o, const char* signal, PassOwnPtr<WorkItem> workItem)
-{
- WorkQueue::WorkItemQt* itemQt = new WorkQueue::WorkItemQt(this, o, signal, workItem.leakPtr());
- itemQt->moveToThread(m_workThread);
- m_signalListeners.add(o, itemQt);
-}
-
-void WorkQueue::disconnectSignal(QObject* o, const char* name)
-{
- HashMap<QObject*, WorkItemQt*>::iterator it = m_signalListeners.find(o);
- for (; it != m_signalListeners.end(); ++it) {
- if (strcmp(it->second->m_signal, name))
- continue;
- delete it->second;
- m_signalListeners.remove(it);
- return;
- }
-}
-
-void WorkQueue::moveSocketToWorkThread(QLocalSocket* socket)
+QSocketNotifier* WorkQueue::registerSocketEventHandler(int socketDescriptor, QSocketNotifier::Type type, PassOwnPtr<WorkItem> workItem)
{
ASSERT(m_workThread);
- ASSERT(socket);
- socket->setParent(0);
- socket->moveToThread(m_workThread);
+ QSocketNotifier* notifier = new QSocketNotifier(socketDescriptor, type, 0);
+ notifier->setEnabled(false);
+ notifier->moveToThread(m_workThread);
+ WorkQueue::WorkItemQt* itemQt = new WorkQueue::WorkItemQt(this, notifier, SIGNAL(activated(int)), workItem.leakPtr());
+ itemQt->moveToThread(m_workThread);
+ notifier->setEnabled(true);
+ return notifier;
}
void WorkQueue::platformInitialize(const char*)
@@ -129,4 +115,10 @@ void WorkQueue::scheduleWorkAfterDelay(PassOwnPtr<WorkItem>, double)
notImplemented();
}
+void WorkQueue::scheduleWorkOnTermination(WebKit::PlatformProcessIdentifier process, PassOwnPtr<WorkItem> workItem)
+{
+ WorkQueue::WorkItemQt* itemQt = new WorkQueue::WorkItemQt(this, process, SIGNAL(finished(int, QProcess::ExitStatus)), workItem.leakPtr());
+ itemQt->moveToThread(m_workThread);
+}
+
#include "WorkQueueQt.moc"
diff --git a/Source/WebKit2/Shared/qt/UpdateChunk.cpp b/Source/WebKit2/Shared/qt/UpdateChunk.cpp
index 4d8e62d..2f9be45 100644
--- a/Source/WebKit2/Shared/qt/UpdateChunk.cpp
+++ b/Source/WebKit2/Shared/qt/UpdateChunk.cpp
@@ -29,7 +29,6 @@
#include "ArgumentDecoder.h"
#include "ArgumentEncoder.h"
-#include "MappedMemoryPool.h"
#include "WebCoreArgumentCoders.h"
#include <QIODevice>
#include <QImage>
@@ -43,28 +42,35 @@ using namespace std;
namespace WebKit {
UpdateChunk::UpdateChunk()
- : m_mappedMemory(0)
{
}
UpdateChunk::UpdateChunk(const IntRect& rect)
: m_rect(rect)
- , m_mappedMemory(MappedMemoryPool::instance()->mapMemory(size()))
+ , m_sharedMemory(SharedMemory::create(size()))
{
}
UpdateChunk::~UpdateChunk()
{
- if (m_mappedMemory)
- m_mappedMemory->markFree();
}
void UpdateChunk::encode(CoreIPC::ArgumentEncoder* encoder) const
{
encoder->encode(m_rect);
- encoder->encode(String(m_mappedMemory->mappedFileName()));
+ if (!m_sharedMemory) {
+ encoder->encode(false);
+ return;
+ }
+
+ SharedMemory::Handle handle;
+ if (m_sharedMemory->createHandle(handle, SharedMemory::ReadOnly)) {
+ encoder->encode(true);
+ encoder->encode(handle);
+ } else
+ encoder->encode(false);
- m_mappedMemory = 0;
+ m_sharedMemory = 0;
}
bool UpdateChunk::decode(CoreIPC::ArgumentDecoder* decoder, UpdateChunk& chunk)
@@ -74,16 +80,23 @@ bool UpdateChunk::decode(CoreIPC::ArgumentDecoder* decoder, UpdateChunk& chunk)
IntRect rect;
if (!decoder->decode(rect))
return false;
+
chunk.m_rect = rect;
- if (chunk.isEmpty())
- return true; // Successfully decoded empty chunk.
+ bool hasSharedMemory;
+ if (!decoder->decode(hasSharedMemory))
+ return false;
- String fileName;
- if (!decoder->decode(fileName))
+ if (!hasSharedMemory) {
+ chunk.m_sharedMemory = 0;
+ return true;
+ }
+
+ SharedMemory::Handle handle;
+ if (!decoder->decode(handle))
return false;
- chunk.m_mappedMemory = MappedMemoryPool::instance()->mapFile(fileName, chunk.size());
+ chunk.m_sharedMemory = SharedMemory::create(handle, SharedMemory::ReadOnly);
return true;
}
@@ -101,7 +114,10 @@ size_t UpdateChunk::size() const
QImage UpdateChunk::createImage() const
{
- ASSERT(m_mappedMemory);
+ ASSERT(m_sharedMemory);
+ if (!m_sharedMemory)
+ return QImage();
+
QImage::Format format;
int bpp;
if (QPixmap::defaultDepth() == 16) {
@@ -112,7 +128,7 @@ QImage UpdateChunk::createImage() const
bpp = 4;
}
- return QImage(m_mappedMemory->data(), m_rect.width(), m_rect.height(), (m_rect.width() * bpp + 3) & ~0x3, format);
+ return QImage(reinterpret_cast<unsigned char*>(m_sharedMemory->data()), m_rect.width(), m_rect.height(), (m_rect.width() * bpp + 3) & ~0x3, format);
}
} // namespace WebKit
diff --git a/Source/WebKit2/Shared/qt/UpdateChunk.h b/Source/WebKit2/Shared/qt/UpdateChunk.h
index f506ba7..664056a 100644
--- a/Source/WebKit2/Shared/qt/UpdateChunk.h
+++ b/Source/WebKit2/Shared/qt/UpdateChunk.h
@@ -29,6 +29,7 @@
#include <QImage>
#include <WebCore/IntRect.h>
+#include "SharedMemory.h"
namespace CoreIPC {
class ArgumentEncoder;
@@ -37,8 +38,6 @@ class ArgumentDecoder;
namespace WebKit {
-class MappedMemory;
-
class UpdateChunk {
public:
UpdateChunk();
@@ -58,7 +57,7 @@ private:
WebCore::IntRect m_rect;
- mutable MappedMemory* m_mappedMemory;
+ mutable RefPtr<SharedMemory> m_sharedMemory;
};
} // namespace WebKit
diff --git a/Source/WebKit2/UIProcess/Launcher/ProcessLauncher.h b/Source/WebKit2/UIProcess/Launcher/ProcessLauncher.h
index 31efd4d..79d1253 100644
--- a/Source/WebKit2/UIProcess/Launcher/ProcessLauncher.h
+++ b/Source/WebKit2/UIProcess/Launcher/ProcessLauncher.h
@@ -72,11 +72,6 @@ public:
static bool getProcessTypeFromString(const char*, ProcessType&);
-#if PLATFORM(QT)
- friend class ProcessLauncherHelper;
- static QLocalSocket* takePendingConnection();
-#endif
-
private:
ProcessLauncher(Client*, const LaunchOptions& launchOptions);
diff --git a/Source/WebKit2/UIProcess/Launcher/qt/ProcessLauncherQt.cpp b/Source/WebKit2/UIProcess/Launcher/qt/ProcessLauncherQt.cpp
index 7dff894..baa5ee7 100644
--- a/Source/WebKit2/UIProcess/Launcher/qt/ProcessLauncherQt.cpp
+++ b/Source/WebKit2/UIProcess/Launcher/qt/ProcessLauncherQt.cpp
@@ -27,17 +27,9 @@
#include "ProcessLauncher.h"
#include "Connection.h"
-#include "CleanupHandler.h"
#include "NotImplemented.h"
#include "RunLoop.h"
#include "WebProcess.h"
-#include <runtime/InitializeThreading.h>
-#include <string>
-#include <wtf/HashSet.h>
-#include <wtf/PassRefPtr.h>
-#include <wtf/Threading.h>
-#include <wtf/text/WTFString.h>
-
#include <QApplication>
#include <QDebug>
#include <QFile>
@@ -45,52 +37,27 @@
#include <QMetaType>
#include <QProcess>
#include <QString>
-
#include <QtCore/qglobal.h>
-
+#include <errno.h>
+#include <fcntl.h>
+#include <runtime/InitializeThreading.h>
+#include <string>
#include <sys/resource.h>
+#include <sys/socket.h>
#include <unistd.h>
+#include <wtf/HashSet.h>
+#include <wtf/PassRefPtr.h>
+#include <wtf/Threading.h>
+#include <wtf/text/WTFString.h>
+#if defined Q_OS_UNIX
+#include <sys/prctl.h>
+#include <signal.h>
+#endif
using namespace WebCore;
namespace WebKit {
-class ProcessLauncherHelper : public QObject {
- Q_OBJECT
-public:
- ~ProcessLauncherHelper();
- void launch(WebKit::ProcessLauncher*);
- QLocalSocket* takePendingConnection();
- static ProcessLauncherHelper* instance();
-
- const QString serverName() const { return m_server.serverName(); }
-
-private:
- ProcessLauncherHelper();
- QLocalServer m_server;
- QList<WorkItem*> m_items;
-
- Q_SLOT void newConnection();
-};
-
-Q_GLOBAL_STATIC(WTF::HashSet<QProcess*>, processes);
-
-static void cleanupAtExit()
-{
- // Terminate our web process(es).
- WTF::HashSet<QProcess*>::const_iterator end = processes()->end();
- for (WTF::HashSet<QProcess*>::const_iterator it = processes()->begin(); it != end; ++it) {
- QProcess* process = *it;
- process->disconnect(process);
- process->terminate();
- if (!process->waitForFinished(200))
- process->kill();
- }
-
- // Do not leave the socket file behind.
- QLocalServer::removeServer(ProcessLauncherHelper::instance()->serverName());
-}
-
class QtWebProcess : public QProcess
{
Q_OBJECT
@@ -98,32 +65,20 @@ public:
QtWebProcess(QObject* parent = 0)
: QProcess(parent)
{
- static bool isRegistered = false;
- if (!isRegistered) {
- qRegisterMetaType<QProcess::ProcessState>("QProcess::ProcessState");
- isRegistered = true;
- }
-
- connect(this, SIGNAL(stateChanged(QProcess::ProcessState)), this, SLOT(processStateChanged(QProcess::ProcessState)));
}
-private slots:
- void processStateChanged(QProcess::ProcessState state);
+protected:
+ virtual void setupChildProcess();
};
-void QtWebProcess::processStateChanged(QProcess::ProcessState state)
+void QtWebProcess::setupChildProcess()
{
- QProcess* process = qobject_cast<QProcess*>(sender());
- if (!process)
- return;
-
- if (state == QProcess::Running)
- processes()->add(process);
- else if (state == QProcess::NotRunning)
- processes()->remove(process);
+#if defined Q_OS_UNIX
+ prctl(PR_SET_PDEATHSIG, SIGKILL);
+#endif
}
-void ProcessLauncherHelper::launch(WebKit::ProcessLauncher* launcher)
+void ProcessLauncher::launchProcess()
{
QString applicationPath = "%1 %2";
@@ -133,12 +88,38 @@ void ProcessLauncherHelper::launch(WebKit::ProcessLauncher* launcher)
applicationPath = applicationPath.arg("QtWebProcess");
}
- QString program(applicationPath.arg(m_server.serverName()));
+ int sockets[2];
+ if (socketpair(AF_UNIX, SOCK_DGRAM, 0, sockets) == -1) {
+ qDebug() << "Creation of socket failed with errno:" << errno;
+ ASSERT_NOT_REACHED();
+ return;
+ }
+
+ // Don't expose the ui socket to the web process
+ while (fcntl(sockets[1], F_SETFD, FD_CLOEXEC == -1)) {
+ if (errno != EINTR) {
+ ASSERT_NOT_REACHED();
+ while (close(sockets[0]) == -1 && errno == EINTR) { }
+ while (close(sockets[1]) == -1 && errno == EINTR) { }
+ return;
+ }
+ }
+
+ QString program(applicationPath.arg(sockets[0]));
QProcess* webProcess = new QtWebProcess();
webProcess->setProcessChannelMode(QProcess::ForwardedChannels);
webProcess->start(program);
+ // Don't expose the web socket to possible future web processes
+ while (fcntl(sockets[0], F_SETFD, FD_CLOEXEC) == -1) {
+ if (errno != EINTR) {
+ ASSERT_NOT_REACHED();
+ delete webProcess;
+ return;
+ }
+ }
+
if (!webProcess->waitForStarted()) {
qDebug() << "Failed to start" << program;
ASSERT_NOT_REACHED();
@@ -148,55 +129,7 @@ void ProcessLauncherHelper::launch(WebKit::ProcessLauncher* launcher)
setpriority(PRIO_PROCESS, webProcess->pid(), 10);
- m_items.append(WorkItem::create(launcher, &WebKit::ProcessLauncher::didFinishLaunchingProcess, webProcess, m_server.serverName()).leakPtr());
-}
-
-QLocalSocket* ProcessLauncherHelper::takePendingConnection()
-{
- return m_server.nextPendingConnection();
-}
-
-ProcessLauncherHelper::~ProcessLauncherHelper()
-{
- m_server.close();
-}
-
-ProcessLauncherHelper::ProcessLauncherHelper()
-{
- srandom(time(0));
- if (!m_server.listen("QtWebKit" + QString::number(random()))) {
- qDebug() << "Failed to create server socket.";
- ASSERT_NOT_REACHED();
- }
- connect(&m_server, SIGNAL(newConnection()), this, SLOT(newConnection()));
-}
-
-ProcessLauncherHelper* ProcessLauncherHelper::instance()
-{
- static ProcessLauncherHelper* result = 0;
- if (!result) {
- result = new ProcessLauncherHelper();
-
- // The purpose of the following line is to ensure that our static is initialized before the exit handler is installed.
- processes()->clear();
-
- atexit(cleanupAtExit);
- }
- return result;
-}
-
-void ProcessLauncherHelper::newConnection()
-{
- ASSERT(!m_items.isEmpty());
-
- m_items[0]->execute();
- delete m_items[0];
- m_items.pop_front();
-}
-
-void ProcessLauncher::launchProcess()
-{
- ProcessLauncherHelper::instance()->launch(this);
+ RunLoop::main()->scheduleWork(WorkItem::create(this, &WebKit::ProcessLauncher::didFinishLaunchingProcess, webProcess, sockets[1]));
}
void ProcessLauncher::terminateProcess()
@@ -208,14 +141,9 @@ void ProcessLauncher::terminateProcess()
m_processIdentifier->terminate();
}
-QLocalSocket* ProcessLauncher::takePendingConnection()
-{
- return ProcessLauncherHelper::instance()->takePendingConnection();
-}
-
void ProcessLauncher::platformInvalidate()
{
- notImplemented();
+
}
} // namespace WebKit
diff --git a/Source/WebKit2/UIProcess/Launcher/qt/ThreadLauncherQt.cpp b/Source/WebKit2/UIProcess/Launcher/qt/ThreadLauncherQt.cpp
index 471a424..344580c 100644
--- a/Source/WebKit2/UIProcess/Launcher/qt/ThreadLauncherQt.cpp
+++ b/Source/WebKit2/UIProcess/Launcher/qt/ThreadLauncherQt.cpp
@@ -54,7 +54,7 @@ static void* webThreadBody(void* /* context */)
// FIXME: We do not support threaded mode for now.
- WebProcess::shared().initialize("foo", RunLoop::current());
+ WebProcess::shared().initialize(-1, RunLoop::current());
RunLoop::run();
return 0;
@@ -70,8 +70,7 @@ CoreIPC::Connection::Identifier ThreadLauncher::createWebThread()
return 0;
}
- QString serverIdentifier = QString::number(connectionIdentifier);
- return serverIdentifier;
+ return connectionIdentifier;
}
} // namespace WebKit
diff --git a/Source/WebKit2/UIProcess/WebProcessProxy.cpp b/Source/WebKit2/UIProcess/WebProcessProxy.cpp
index c7e9382..6d115dc 100644
--- a/Source/WebKit2/UIProcess/WebProcessProxy.cpp
+++ b/Source/WebKit2/UIProcess/WebProcessProxy.cpp
@@ -344,8 +344,10 @@ void WebProcessProxy::didFinishLaunching(CoreIPC::Connection::Identifier connect
m_connection = CoreIPC::Connection::createServerConnection(connectionIdentifier, this, RunLoop::main());
#if PLATFORM(MAC)
m_connection->setShouldCloseConnectionOnMachExceptions();
+#elif PLATFORM(QT)
+ m_connection->setShouldCloseConnectionOnProcessTermination(processIdentifier());
#endif
-
+
m_connection->open();
for (size_t i = 0; i < m_pendingMessages.size(); ++i) {
diff --git a/Source/WebKit2/UIProcess/qt/WebContextQt.cpp b/Source/WebKit2/UIProcess/qt/WebContextQt.cpp
index 5b2cd88..f6b846d 100644
--- a/Source/WebKit2/UIProcess/qt/WebContextQt.cpp
+++ b/Source/WebKit2/UIProcess/qt/WebContextQt.cpp
@@ -28,6 +28,7 @@
#include "ApplicationCacheStorage.h"
#include "WebProcessCreationParameters.h"
+#include <QProcess>
namespace WebKit {
@@ -42,6 +43,7 @@ String WebContext::applicationCacheDirectory()
void WebContext::platformInitializeWebProcess(WebProcessCreationParameters&)
{
+ qRegisterMetaType<QProcess::ExitStatus>("QProcess::ExitStatus");
}
} // namespace WebKit
diff --git a/Source/WebKit2/WebKit2.pro b/Source/WebKit2/WebKit2.pro
index ed6bf1b..ea98904 100644
--- a/Source/WebKit2/WebKit2.pro
+++ b/Source/WebKit2/WebKit2.pro
@@ -232,7 +232,6 @@ HEADERS += \
Platform/SharedMemory.h \
Platform/WorkItem.h \
Platform/WorkQueue.h \
- Platform/qt/MappedMemoryPool.h \
Shared/API/c/WKBase.h \
Shared/API/c/WKCertificateInfo.h \
Shared/API/c/WKContextMenuItem.h \
@@ -293,7 +292,6 @@ HEADERS += \
Shared/WebURLResponse.h \
Shared/WebUserContentURLPattern.h \
Shared/Plugins/Netscape/NetscapePluginModule.h \
- Shared/qt/CleanupHandler.h \
Shared/qt/PlatformCertificateInfo.h \
Shared/qt/UpdateChunk.h \
Shared/qt/WebEventFactoryQt.h \
@@ -459,12 +457,12 @@ SOURCES += \
Platform/CoreIPC/BinarySemaphore.cpp \
Platform/CoreIPC/Connection.cpp \
Platform/CoreIPC/DataReference.cpp \
+ Platform/CoreIPC/qt/AttachmentQt.cpp \
Platform/CoreIPC/qt/ConnectionQt.cpp \
Platform/Logging.cpp \
Platform/Module.cpp \
Platform/RunLoop.cpp \
Platform/WorkQueue.cpp \
- Platform/qt/MappedMemoryPool.cpp \
Platform/qt/ModuleQt.cpp \
Platform/qt/RunLoopQt.cpp \
Platform/qt/SharedMemoryQt.cpp \
@@ -517,7 +515,6 @@ SOURCES += \
Shared/WebURLResponse.cpp \
Shared/WebWheelEvent.cpp \
Shared/qt/ShareableBitmapQt.cpp \
- Shared/qt/CleanupHandler.cpp \
Shared/qt/NativeWebKeyboardEventQt.cpp \
Shared/qt/UpdateChunk.cpp \
Shared/qt/WebCoreArgumentCodersQt.cpp \
diff --git a/Source/WebKit2/WebProcess/qt/WebProcessMainQt.cpp b/Source/WebKit2/WebProcess/qt/WebProcessMainQt.cpp
index bd4e370..3e122ff 100644
--- a/Source/WebKit2/WebProcess/qt/WebProcessMainQt.cpp
+++ b/Source/WebKit2/WebProcess/qt/WebProcessMainQt.cpp
@@ -160,7 +160,18 @@ QWEBKIT_EXPORT int WebProcessMainQt(int argc, char** argv)
RunLoop::initializeMainRunLoop();
// Create the connection.
- QString identifier(app->arguments().size() > 1 ? app->arguments().at(1) : "");
+ if (app->arguments().size() <= 1) {
+ qDebug() << "Error: wrong number of arguments.";
+ return 1;
+ }
+
+ bool wasNumber = false;
+ int identifier = app->arguments().at(1).toInt(&wasNumber, 10);
+ if (!wasNumber) {
+ qDebug() << "Error: connection identifier wrong.";
+ return 1;
+ }
+
WebKit::WebProcess::shared().initialize(identifier, RunLoop::main());
RunLoop::run();
--
WebKit Debian packaging
More information about the Pkg-webkit-commits
mailing list