WebKit Bugzilla
New
Browse
Search+
Log In
×
Sign in with GitHub
or
Remember my login
Create Account
·
Forgot Password
Forgotten password account recovery
[patch]
Patch
bug-228168-20210729130209.patch (text/plain), 49.40 KB, created by
Chris Dumez
on 2021-07-29 13:02:10 PDT
(
hide
)
Description:
Patch
Filename:
MIME Type:
Creator:
Chris Dumez
Created:
2021-07-29 13:02:10 PDT
Size:
49.40 KB
patch
obsolete
>Subversion Revision: 280427 >diff --git a/Source/WebCore/ChangeLog b/Source/WebCore/ChangeLog >index 3dabc55867d0591c2b32df2f0dfe2cfb325e71a7..1e1ef8274e0634a23143e41b7396f115df1badec 100644 >--- a/Source/WebCore/ChangeLog >+++ b/Source/WebCore/ChangeLog >@@ -1,3 +1,70 @@ >+2021-07-29 Chris Dumez <cdumez@apple.com> >+ >+ imported/w3c/web-platform-tests/webmessaging/broadcastchannel/blobs.html is a flaky failure since implementing BlobChannel >+ https://bugs.webkit.org/show_bug.cgi?id=228168 >+ <rdar://problem/80922502> >+ >+ Reviewed by NOBODY (OOPS!). >+ >+ The test was flaky because it is trying to send a Blob via BroadcastChannel.postMessage() >+ without keeping the blob alive. When GC triggers, the Blob would go away and trying to >+ decode the Blob upon receiving would fail. >+ >+ To address the issue, I introduced a Blob::Handle class that wraps the Blob's internal URL >+ and keeps the Blob data alive as long as as someone is holding such handle. Previously, >+ the Blob destructor would unregister the internal URL and the Blob data would go away. >+ >+ I then updated SerializedScriptValue to hold on to Blob::Handle objects instead of Blob >+ URLs. This guarantees that when using postMessage() to send a message to a worker, the >+ Blob data will stay alive until we dispatch the message event on the worker side and try >+ and deserialized the SerializedScriptValue. >+ >+ For BroadcastChannel.postMessage() though, we end up going via the network process and >+ the SerializedScriptValue ends up getting serialized/deserialized over IPC. I added a >+ CompletionHandler to BroadcastChannelRegistry::postMessage() which only gets called >+ once the message event has successfully been dispatched. I use this completion handler >+ to make sure the SerializedScriptValue's Blob URLs stay valid until the the message has >+ been dispatched by holding on to the Blob::Handles. >+ >+ No new tests, unskipped existing test. >+ >+ * Modules/indexeddb/IDBValue.cpp: >+ (WebCore::IDBValue::IDBValue): >+ * bindings/js/SerializedScriptValue.cpp: >+ (WebCore::CloneSerializer::serialize): >+ (WebCore::CloneSerializer::CloneSerializer): >+ (WebCore::CloneSerializer::dumpIfTerminal): >+ (WebCore::CloneSerializer::write): >+ (WebCore::SerializedScriptValue::SerializedScriptValue): >+ (WebCore::SerializedScriptValue::computeMemoryCost const): >+ (WebCore::SerializedScriptValue::create): >+ (WebCore::SerializedScriptValue::blobURLs const): >+ (WebCore::SerializedScriptValue::writeBlobsToDiskForIndexedDB): >+ * bindings/js/SerializedScriptValue.h: >+ (WebCore::SerializedScriptValue::hasBlobURLs const): >+ (WebCore::SerializedScriptValue::blobHandles const): >+ (WebCore::SerializedScriptValue::SerializedScriptValue): >+ * dom/BroadcastChannel.cpp: >+ (WebCore::BroadcastChannel::postMessage): >+ (WebCore::BroadcastChannel::dispatchMessageTo): >+ * dom/BroadcastChannel.h: >+ * dom/BroadcastChannelRegistry.h: >+ * fileapi/Blob.cpp: >+ (WebCore::BlobInternalURL::create): >+ (WebCore::BlobInternalURL::~BlobInternalURL): >+ (WebCore::BlobInternalURL::url const): >+ (WebCore::BlobInternalURL::BlobInternalURL): >+ (WebCore::Blob::Blob): >+ (WebCore::Blob::~Blob): >+ (WebCore::Blob::url const): >+ (WebCore::Blob::slice const): >+ (WebCore::Blob::size const): >+ (WebCore::Blob::handle const): >+ (WebCore::Blob::Handle::Handle): >+ (WebCore::Blob::Handle::url const): >+ * fileapi/Blob.h: >+ * loader/EmptyClients.cpp: >+ > 2021-07-29 Adrian Perez de Castro <aperez@igalia.com> > > [CMake] Use an imported target for the libgcrypt library >diff --git a/Source/WebKit/ChangeLog b/Source/WebKit/ChangeLog >index c0b0b64a36f980341077dcf973165136d198ce05..427d5f6c1833d99fd65e64fce3007432b0f5f2ba 100644 >--- a/Source/WebKit/ChangeLog >+++ b/Source/WebKit/ChangeLog >@@ -1,3 +1,27 @@ >+2021-07-29 Chris Dumez <cdumez@apple.com> >+ >+ imported/w3c/web-platform-tests/webmessaging/broadcastchannel/blobs.html is a flaky failure since implementing BlobChannel >+ https://bugs.webkit.org/show_bug.cgi?id=228168 >+ <rdar://problem/80922502> >+ >+ Reviewed by NOBODY (OOPS!). >+ >+ * NetworkProcess/NetworkBroadcastChannelRegistry.cpp: >+ (WebKit::NetworkBroadcastChannelRegistry::postMessage): >+ * NetworkProcess/NetworkBroadcastChannelRegistry.h: >+ * NetworkProcess/NetworkBroadcastChannelRegistry.messages.in: >+ >+ * Platform/IPC/HandleMessage.h: >+ (IPC::handleMessageAsyncWantsConnection): >+ handleMessageAsyncWantsConnection() had gotten out of sync with handleMessageAsync(). This was causing IPC decoding >+ failures when using both "Async" and "WantsConnection" for the IPC message. >+ >+ * WebProcess/WebCoreSupport/WebBroadcastChannelRegistry.cpp: >+ (WebKit::WebBroadcastChannelRegistry::postMessage): >+ (WebKit::WebBroadcastChannelRegistry::postMessageToRemote): >+ * WebProcess/WebCoreSupport/WebBroadcastChannelRegistry.h: >+ * WebProcess/WebCoreSupport/WebBroadcastChannelRegistry.messages.in: >+ > 2021-07-29 Kate Cheney <katherine_cheney@apple.com> > > CORS preflight checks not attributed to the correct application >diff --git a/Source/WebKitLegacy/ChangeLog b/Source/WebKitLegacy/ChangeLog >index 5a93a4d7ef095acc810e669cbca4b25f4fe042df..55550ff6cf010b65d2fcd57be686703881ac857b 100644 >--- a/Source/WebKitLegacy/ChangeLog >+++ b/Source/WebKitLegacy/ChangeLog >@@ -1,3 +1,15 @@ >+2021-07-29 Chris Dumez <cdumez@apple.com> >+ >+ imported/w3c/web-platform-tests/webmessaging/broadcastchannel/blobs.html is a flaky failure since implementing BlobChannel >+ https://bugs.webkit.org/show_bug.cgi?id=228168 >+ <rdar://problem/80922502> >+ >+ Reviewed by NOBODY (OOPS!). >+ >+ * WebCoreSupport/WebBroadcastChannelRegistry.cpp: >+ (WebBroadcastChannelRegistry::postMessage): >+ * WebCoreSupport/WebBroadcastChannelRegistry.h: >+ > 2021-07-19 Sihui Liu <sihui_liu@apple.com> > > Implement IDBTransaction.commit() >diff --git a/Source/WebCore/Modules/indexeddb/IDBValue.cpp b/Source/WebCore/Modules/indexeddb/IDBValue.cpp >index 8c7f11968b3e9f2489d8da0d2aa0f08f6f5407cd..a361113ddc527ee7b899623349770e158e71aa18 100644 >--- a/Source/WebCore/Modules/indexeddb/IDBValue.cpp >+++ b/Source/WebCore/Modules/indexeddb/IDBValue.cpp >@@ -37,7 +37,7 @@ IDBValue::IDBValue() > > IDBValue::IDBValue(const SerializedScriptValue& scriptValue) > : m_data(ThreadSafeDataBuffer::copyVector(scriptValue.data())) >- , m_blobURLs(scriptValue.blobURLsIsolatedCopy()) >+ , m_blobURLs(scriptValue.blobURLs()) > { > } > >diff --git a/Source/WebCore/bindings/js/SerializedScriptValue.cpp b/Source/WebCore/bindings/js/SerializedScriptValue.cpp >index f2e4a7acea7032db333e44bdacae7387b581ab9b..4d300712c0fb722df5dda779c64414498f104189 100644 >--- a/Source/WebCore/bindings/js/SerializedScriptValue.cpp >+++ b/Source/WebCore/bindings/js/SerializedScriptValue.cpp >@@ -600,7 +600,7 @@ public: > WasmModuleArray& wasmModules, > WasmMemoryHandleArray& wasmMemoryHandles, > #endif >- Vector<String>& blobURLs, Vector<uint8_t>& out, SerializationContext context, ArrayBufferContentsArray& sharedBuffers) >+ Vector<Blob::Handle>& blobHandles, Vector<uint8_t>& out, SerializationContext context, ArrayBufferContentsArray& sharedBuffers) > { > CloneSerializer serializer(lexicalGlobalObject, messagePorts, arrayBuffers, imageBitmaps, > #if ENABLE(OFFSCREEN_CANVAS_IN_WORKERS) >@@ -613,7 +613,7 @@ public: > wasmModules, > wasmMemoryHandles, > #endif >- blobURLs, out, context, sharedBuffers); >+ blobHandles, out, context, sharedBuffers); > return serializer.serialize(value); > } > >@@ -647,10 +647,10 @@ private: > WasmModuleArray& wasmModules, > WasmMemoryHandleArray& wasmMemoryHandles, > #endif >- Vector<String>& blobURLs, Vector<uint8_t>& out, SerializationContext context, ArrayBufferContentsArray& sharedBuffers) >+ Vector<Blob::Handle>& blobHandles, Vector<uint8_t>& out, SerializationContext context, ArrayBufferContentsArray& sharedBuffers) > : CloneBase(lexicalGlobalObject) > , m_buffer(out) >- , m_blobURLs(blobURLs) >+ , m_blobHandles(blobHandles) > , m_emptyIdentifier(Identifier::fromString(lexicalGlobalObject->vm(), emptyString())) > , m_context(context) > , m_sharedBuffers(sharedBuffers) >@@ -1224,7 +1224,7 @@ private: > } > if (auto* blob = JSBlob::toWrapped(vm, obj)) { > write(BlobTag); >- m_blobURLs.append(blob->url().string()); >+ m_blobHandles.append(blob->handle()); > write(blob->url().string()); > write(blob->type()); > write(blob->size()); >@@ -1297,7 +1297,7 @@ private: > if (auto* key = JSCryptoKey::toWrapped(vm, obj)) { > write(CryptoKeyTag); > Vector<uint8_t> serializedKey; >- Vector<String> dummyBlobURLs; >+ Vector<Blob::Handle> dummyBlobHandles; > Vector<RefPtr<MessagePort>> dummyMessagePorts; > Vector<RefPtr<JSC::ArrayBuffer>> dummyArrayBuffers; > #if ENABLE(WEBASSEMBLY) >@@ -1316,7 +1316,7 @@ private: > dummyModules, > dummyMemoryHandles, > #endif >- dummyBlobURLs, serializedKey, SerializationContext::Default, dummySharedBuffers); >+ dummyBlobHandles, serializedKey, SerializationContext::Default, dummySharedBuffers); > rawKeySerializer.write(key); > Vector<uint8_t> wrappedKey; > if (!wrapCryptoKey(m_lexicalGlobalObject, serializedKey, wrappedKey)) >@@ -1550,7 +1550,7 @@ private: > > void write(const File& file) > { >- m_blobURLs.append(file.url().string()); >+ m_blobHandles.append(file.handle()); > write(file.path()); > write(file.url().string()); > write(file.type()); >@@ -1760,7 +1760,7 @@ private: > } > > Vector<uint8_t>& m_buffer; >- Vector<String>& m_blobURLs; >+ Vector<Blob::Handle>& m_blobHandles; > ObjectPool m_objectPool; > ObjectPool m_transferredMessagePorts; > ObjectPool m_transferredArrayBuffers; >@@ -3915,7 +3915,7 @@ SerializedScriptValue::SerializedScriptValue(Vector<uint8_t>&& buffer, std::uniq > m_memoryCost = computeMemoryCost(); > } > >-SerializedScriptValue::SerializedScriptValue(Vector<uint8_t>&& buffer, const Vector<String>& blobURLs, std::unique_ptr<ArrayBufferContentsArray> arrayBufferContentsArray, std::unique_ptr<ArrayBufferContentsArray> sharedBufferContentsArray, Vector<std::optional<ImageBitmapBacking>>&& backingStores >+SerializedScriptValue::SerializedScriptValue(Vector<uint8_t>&& buffer, const Vector<Blob::Handle>& blobHandles, std::unique_ptr<ArrayBufferContentsArray> arrayBufferContentsArray, std::unique_ptr<ArrayBufferContentsArray> sharedBufferContentsArray, Vector<std::optional<ImageBitmapBacking>>&& backingStores > #if ENABLE(OFFSCREEN_CANVAS_IN_WORKERS) > , Vector<std::unique_ptr<DetachedOffscreenCanvas>>&& detachedOffscreenCanvases > #endif >@@ -3941,12 +3941,8 @@ SerializedScriptValue::SerializedScriptValue(Vector<uint8_t>&& buffer, const Vec > , m_wasmModulesArray(WTFMove(wasmModulesArray)) > , m_wasmMemoryHandlesArray(WTFMove(wasmMemoryHandlesArray)) > #endif >+ , m_blobHandles(blobHandles) > { >- // Since this SerializedScriptValue is meant to be passed between threads, its String data members >- // need to be isolatedCopies so we don't run into thread safety issues for the StringImpls. >- m_blobURLs.reserveInitialCapacity(blobURLs.size()); >- for (auto& url : blobURLs) >- m_blobURLs.uncheckedAppend(url.isolatedCopy()); > m_memoryCost = computeMemoryCost(); > } > >@@ -3990,8 +3986,8 @@ size_t SerializedScriptValue::computeMemoryCost() const > } > #endif > >- for (auto& urls : m_blobURLs) >- cost += urls.sizeInBytes(); >+ for (auto& handle : m_blobHandles) >+ cost += handle.url().string().sizeInBytes(); > > return cost; > } >@@ -4069,7 +4065,7 @@ static Exception exceptionForSerializationFailure(SerializationReturnCode code) > RefPtr<SerializedScriptValue> SerializedScriptValue::create(JSGlobalObject& lexicalGlobalObject, JSValue value, SerializationErrorMode throwExceptions) > { > Vector<uint8_t> buffer; >- Vector<String> blobURLs; >+ Vector<Blob::Handle> blobHandles; > Vector<RefPtr<MessagePort>> dummyMessagePorts; > Vector<RefPtr<ImageBitmap>> dummyImageBitmaps; > #if ENABLE(OFFSCREEN_CANVAS_IN_WORKERS) >@@ -4095,7 +4091,7 @@ RefPtr<SerializedScriptValue> SerializedScriptValue::create(JSGlobalObject& lexi > dummyModules, > dummyMemoryHandles, > #endif >- blobURLs, buffer, SerializationContext::Default, dummySharedBuffers); >+ blobHandles, buffer, SerializationContext::Default, dummySharedBuffers); > > #if ENABLE(WEBASSEMBLY) > ASSERT_WITH_MESSAGE(dummyModules.isEmpty(), "Wasm::Module serialization is only allowed in the postMessage context"); >@@ -4108,7 +4104,7 @@ RefPtr<SerializedScriptValue> SerializedScriptValue::create(JSGlobalObject& lexi > if (code != SerializationReturnCode::SuccessfullyCompleted) > return nullptr; > >- return adoptRef(*new SerializedScriptValue(WTFMove(buffer), blobURLs, nullptr, nullptr, { })); >+ return adoptRef(*new SerializedScriptValue(WTFMove(buffer), blobHandles, nullptr, nullptr, { })); > } > > static bool containsDuplicates(const Vector<RefPtr<ImageBitmap>>& imageBitmaps) >@@ -4217,7 +4213,7 @@ ExceptionOr<Ref<SerializedScriptValue>> SerializedScriptValue::create(JSGlobalOb > #endif > > Vector<uint8_t> buffer; >- Vector<String> blobURLs; >+ Vector<Blob::Handle> blobHandles; > #if ENABLE(WEBASSEMBLY) > WasmModuleArray wasmModules; > WasmMemoryHandleArray wasmMemoryHandles; >@@ -4234,7 +4230,7 @@ ExceptionOr<Ref<SerializedScriptValue>> SerializedScriptValue::create(JSGlobalOb > wasmModules, > wasmMemoryHandles, > #endif >- blobURLs, buffer, context, *sharedBuffers); >+ blobHandles, buffer, context, *sharedBuffers); > > if (code != SerializationReturnCode::SuccessfullyCompleted) > return exceptionForSerializationFailure(code); >@@ -4256,7 +4252,7 @@ ExceptionOr<Ref<SerializedScriptValue>> SerializedScriptValue::create(JSGlobalOb > detachedRTCDataChannels.append(channel->detach()); > #endif > >- return adoptRef(*new SerializedScriptValue(WTFMove(buffer), blobURLs, arrayBufferContentsArray.releaseReturnValue(), context == SerializationContext::WorkerPostMessage ? WTFMove(sharedBuffers) : nullptr, WTFMove(backingStores) >+ return adoptRef(*new SerializedScriptValue(WTFMove(buffer), blobHandles, arrayBufferContentsArray.releaseReturnValue(), context == SerializationContext::WorkerPostMessage ? WTFMove(sharedBuffers) : nullptr, WTFMove(backingStores) > #if ENABLE(OFFSCREEN_CANVAS_IN_WORKERS) > , WTFMove(detachedCanvases) > #endif >@@ -4362,12 +4358,12 @@ uint32_t SerializedScriptValue::wireFormatVersion() > return CurrentVersion; > } > >-Vector<String> SerializedScriptValue::blobURLsIsolatedCopy() const >+Vector<String> SerializedScriptValue::blobURLs() const > { > Vector<String> result; >- result.reserveInitialCapacity(m_blobURLs.size()); >- for (auto& url : m_blobURLs) >- result.uncheckedAppend(url.isolatedCopy()); >+ result.reserveInitialCapacity(m_blobHandles.size()); >+ for (auto& handle : m_blobHandles) >+ result.uncheckedAppend(handle.url().string()); > > return result; > } >@@ -4377,7 +4373,7 @@ void SerializedScriptValue::writeBlobsToDiskForIndexedDB(CompletionHandler<void( > ASSERT(isMainThread()); > ASSERT(hasBlobURLs()); > >- blobRegistry().writeBlobsToTemporaryFiles(m_blobURLs, [completionHandler = WTFMove(completionHandler), this, protectedThis = makeRef(*this)] (auto&& blobFilePaths) mutable { >+ blobRegistry().writeBlobsToTemporaryFiles(blobURLs(), [completionHandler = WTFMove(completionHandler), this, protectedThis = makeRef(*this)] (auto&& blobFilePaths) mutable { > ASSERT(isMainThread()); > > if (blobFilePaths.isEmpty()) { >@@ -4387,9 +4383,9 @@ void SerializedScriptValue::writeBlobsToDiskForIndexedDB(CompletionHandler<void( > return; > } > >- ASSERT(m_blobURLs.size() == blobFilePaths.size()); >+ ASSERT(m_blobHandles.size() == blobFilePaths.size()); > >- completionHandler({ *this, m_blobURLs, blobFilePaths }); >+ completionHandler({ *this, blobURLs(), blobFilePaths }); > }); > } > >diff --git a/Source/WebCore/bindings/js/SerializedScriptValue.h b/Source/WebCore/bindings/js/SerializedScriptValue.h >index 1c7545ecb571393f2858360adc01e8c898e650bf..16c49195ffc4f6e6977a7488b4d6c298549a38b4 100644 >--- a/Source/WebCore/bindings/js/SerializedScriptValue.h >+++ b/Source/WebCore/bindings/js/SerializedScriptValue.h >@@ -26,6 +26,7 @@ > > #pragma once > >+#include "Blob.h" > #include "DetachedRTCDataChannel.h" > #include "ExceptionOr.h" > #include <JavaScriptCore/ArrayBuffer.h> >@@ -95,9 +96,10 @@ public: > WEBCORE_EXPORT JSValueRef deserialize(JSContextRef, JSValueRef* exception); > > const Vector<uint8_t>& data() const { return m_data; } >- bool hasBlobURLs() const { return !m_blobURLs.isEmpty(); } >+ bool hasBlobURLs() const { return !m_blobHandles.isEmpty(); } > >- Vector<String> blobURLsIsolatedCopy() const; >+ Vector<String> blobURLs() const; >+ const Vector<Blob::Handle>& blobHandles() const { return m_blobHandles; } > void writeBlobsToDiskForIndexedDB(CompletionHandler<void(IDBValue&&)>&&); > IDBValue writeBlobsToDiskForIndexedDBSynchronously(); > static Ref<SerializedScriptValue> createFromWireBytes(Vector<uint8_t>&& data) >@@ -121,7 +123,7 @@ private: > #endif > ); > >- SerializedScriptValue(Vector<unsigned char>&&, const Vector<String>& blobURLs, std::unique_ptr<ArrayBufferContentsArray>, std::unique_ptr<ArrayBufferContentsArray> sharedBuffers, Vector<std::optional<ImageBitmapBacking>>&& backingStores >+ SerializedScriptValue(Vector<unsigned char>&&, const Vector<Blob::Handle>& blobHandles, std::unique_ptr<ArrayBufferContentsArray>, std::unique_ptr<ArrayBufferContentsArray> sharedBuffers, Vector<std::optional<ImageBitmapBacking>>&& backingStores > #if ENABLE(OFFSCREEN_CANVAS_IN_WORKERS) > , Vector<std::unique_ptr<DetachedOffscreenCanvas>>&& = { } > #endif >@@ -150,7 +152,7 @@ private: > std::unique_ptr<WasmModuleArray> m_wasmModulesArray; > std::unique_ptr<WasmMemoryHandleArray> m_wasmMemoryHandlesArray; > #endif >- Vector<String> m_blobURLs; >+ Vector<Blob::Handle> m_blobHandles; > size_t m_memoryCost { 0 }; > }; > >diff --git a/Source/WebCore/dom/BroadcastChannel.cpp b/Source/WebCore/dom/BroadcastChannel.cpp >index 8271d1f498d5f871d6fad422c6d087c0bce2bd1e..66401bb0bfb438c8ed4170b138927cfd2498eec1 100644 >--- a/Source/WebCore/dom/BroadcastChannel.cpp >+++ b/Source/WebCore/dom/BroadcastChannel.cpp >@@ -34,6 +34,7 @@ > #include "SerializedScriptValue.h" > #include "WorkerGlobalScope.h" > #include "WorkerLoaderProxy.h" >+#include <wtf/CallbackAggregator.h> > #include <wtf/HashMap.h> > #include <wtf/IsoMallocInlines.h> > #include <wtf/MainThread.h> >@@ -95,8 +96,14 @@ ExceptionOr<void> BroadcastChannel::postMessage(JSC::JSGlobalObject& globalObjec > ASSERT(ports.isEmpty()); > > ensureOnMainThread([origin = crossThreadCopy(m_origin), name = crossThreadCopy(m_name), identifier = m_identifier, messageData = messageData.releaseReturnValue()](auto& document) mutable { >- if (auto* page = document.page()) >- page->broadcastChannelRegistry().postMessage(origin, name, identifier, WTFMove(messageData)); >+ auto* page = document.page(); >+ if (!page) >+ return; >+ >+ auto blobHandles = messageData->blobHandles(); >+ page->broadcastChannelRegistry().postMessage(origin, name, identifier, WTFMove(messageData), [blobHandles = WTFMove(blobHandles)] { >+ // Keeps Blob data inside messageData alive until the message has been delivered. >+ }); > }); > > return { }; >@@ -115,14 +122,15 @@ void BroadcastChannel::close() > }); > } > >-void BroadcastChannel::dispatchMessageTo(BroadcastChannelIdentifier channelIdentifier, Ref<SerializedScriptValue>&& message) >+void BroadcastChannel::dispatchMessageTo(BroadcastChannelIdentifier channelIdentifier, Ref<SerializedScriptValue>&& message, CompletionHandler<void()>&& completionHandler) > { > ASSERT(isMainThread()); > auto contextIdentifier = channelToContextIdentifier().get(channelIdentifier); > if (!contextIdentifier) >- return; >+ return completionHandler(); > >- ScriptExecutionContext::postTaskTo(contextIdentifier, [channelIdentifier, message = WTFMove(message)](auto&) mutable { >+ auto callbackAggregator = CallbackAggregator::create(WTFMove(completionHandler)); >+ ScriptExecutionContext::postTaskTo(contextIdentifier, [channelIdentifier, message = WTFMove(message), callbackAggregator = WTFMove(callbackAggregator)](auto&) mutable { > RefPtr<BroadcastChannel> channel; > { > Locker locker { allBroadcastChannelsLock }; >@@ -130,6 +138,8 @@ void BroadcastChannel::dispatchMessageTo(BroadcastChannelIdentifier channelIdent > } > if (channel) > channel->dispatchMessage(WTFMove(message)); >+ >+ callOnMainThread([callbackAggregator = WTFMove(callbackAggregator)] { }); > }); > } > >diff --git a/Source/WebCore/dom/BroadcastChannel.h b/Source/WebCore/dom/BroadcastChannel.h >index 1ff58bda76622214d6b004bfbd98c28ddb045cd3..3dba8f8edc40bc367c57d3bc9953e294f4540109 100644 >--- a/Source/WebCore/dom/BroadcastChannel.h >+++ b/Source/WebCore/dom/BroadcastChannel.h >@@ -62,7 +62,7 @@ public: > ExceptionOr<void> postMessage(JSC::JSGlobalObject&, JSC::JSValue message); > void close(); > >- WEBCORE_EXPORT static void dispatchMessageTo(BroadcastChannelIdentifier, Ref<SerializedScriptValue>&&); >+ WEBCORE_EXPORT static void dispatchMessageTo(BroadcastChannelIdentifier, Ref<SerializedScriptValue>&&, CompletionHandler<void()>&&); > > private: > BroadcastChannel(ScriptExecutionContext&, const String& name); >diff --git a/Source/WebCore/dom/BroadcastChannelRegistry.h b/Source/WebCore/dom/BroadcastChannelRegistry.h >index fa6ebc89493a9e58decab3f49d2d5b94efb74d68..5c2bfb0547f36156beea1df1cdb5f3fd0a35eba2 100644 >--- a/Source/WebCore/dom/BroadcastChannelRegistry.h >+++ b/Source/WebCore/dom/BroadcastChannelRegistry.h >@@ -26,6 +26,7 @@ > #pragma once > > #include "BroadcastChannelIdentifier.h" >+#include <wtf/Forward.h> > #include <wtf/RefCounted.h> > > namespace WebCore { >@@ -38,7 +39,7 @@ public: > virtual ~BroadcastChannelRegistry() { } > virtual void registerChannel(const SecurityOriginData&, const String& name, BroadcastChannelIdentifier) = 0; > virtual void unregisterChannel(const SecurityOriginData&, const String& name, BroadcastChannelIdentifier) = 0; >- virtual void postMessage(const SecurityOriginData&, const String& name, BroadcastChannelIdentifier source, Ref<SerializedScriptValue>&&) = 0; >+ virtual void postMessage(const SecurityOriginData&, const String& name, BroadcastChannelIdentifier source, Ref<SerializedScriptValue>&&, CompletionHandler<void()>&&) = 0; > }; > > } // namespace WebCore >diff --git a/Source/WebCore/fileapi/Blob.cpp b/Source/WebCore/fileapi/Blob.cpp >index 3f409a47ed3b5fd6fd91e9be7f8f0b6236dc7b1e..523cfeb6398acf114eba6f4cbf19fd2ba1df4a44 100644 >--- a/Source/WebCore/fileapi/Blob.cpp >+++ b/Source/WebCore/fileapi/Blob.cpp >@@ -44,6 +44,7 @@ > #include "ThreadableBlobRegistry.h" > #include <wtf/IsoMallocInlines.h> > #include <wtf/NeverDestroyed.h> >+#include <wtf/ThreadSafeRefCounted.h> > #include <wtf/text/CString.h> > > namespace WebCore { >@@ -58,7 +59,6 @@ public: > static URLRegistry& registry(); > }; > >- > void BlobURLRegistry::registerURL(ScriptExecutionContext& context, const URL& publicURL, URLRegistrable& blob) > { > ASSERT(&blob.registry() == this); >@@ -76,24 +76,53 @@ URLRegistry& BlobURLRegistry::registry() > return instance; > } > >+// Unregisters the Blob's internal URL upon destruction. This can be used to extend the lifetime of the Blob data >+// without actually keeping the Blob object alive. >+class BlobInternalURL : public ThreadSafeRefCounted<BlobInternalURL> { >+public: >+ static Ref<BlobInternalURL> create() >+ { >+ return adoptRef(*new BlobInternalURL(BlobURL::createInternalURL())); >+ } >+ >+ static Ref<BlobInternalURL> create(URL&& url) >+ { >+ return adoptRef(*new BlobInternalURL(crossThreadCopy(url))); >+ } >+ >+ ~BlobInternalURL() >+ { >+ ThreadableBlobRegistry::unregisterBlobURL(m_internalURL); >+ } >+ >+ URL url() const { return m_internalURL.isolatedCopy(); } >+ >+private: >+ BlobInternalURL(URL&& internalURL) >+ : m_internalURL(WTFMove(internalURL)) >+ { } >+ >+ URL m_internalURL; >+}; >+ > Blob::Blob(UninitializedContructor, ScriptExecutionContext* context, URL&& url, String&& type) > : ActiveDOMObject(context) >- , m_internalURL(WTFMove(url)) >+ , m_internalURL(BlobInternalURL::create(WTFMove(url))) > , m_type(WTFMove(type)) > { > } > > Blob::Blob(ScriptExecutionContext* context) > : ActiveDOMObject(context) >+ , m_internalURL(BlobInternalURL::create()) > , m_size(0) > { >- m_internalURL = BlobURL::createInternalURL(); >- ThreadableBlobRegistry::registerBlobURL(m_internalURL, { }, { }); >+ ThreadableBlobRegistry::registerBlobURL(m_internalURL->url(), { }, { }); > } > > Blob::Blob(ScriptExecutionContext& context, Vector<BlobPartVariant>&& blobPartVariants, const BlobPropertyBag& propertyBag) > : ActiveDOMObject(&context) >- , m_internalURL(BlobURL::createInternalURL()) >+ , m_internalURL(BlobInternalURL::create()) > , m_type(normalizedContentType(propertyBag.type)) > { > BlobBuilder builder(propertyBag.endings); >@@ -105,56 +134,66 @@ Blob::Blob(ScriptExecutionContext& context, Vector<BlobPartVariant>&& blobPartVa > ); > } > >- ThreadableBlobRegistry::registerBlobURL(m_internalURL, builder.finalize(), m_type); >+ ThreadableBlobRegistry::registerBlobURL(m_internalURL->url(), builder.finalize(), m_type); > } > > Blob::Blob(ScriptExecutionContext* context, Vector<uint8_t>&& data, const String& contentType) > : ActiveDOMObject(context) >+ , m_internalURL(BlobInternalURL::create()) > , m_type(contentType) > , m_size(data.size()) > { > Vector<BlobPart> blobParts; > blobParts.append(BlobPart(WTFMove(data))); >- m_internalURL = BlobURL::createInternalURL(); >- ThreadableBlobRegistry::registerBlobURL(m_internalURL, WTFMove(blobParts), contentType); >+ ThreadableBlobRegistry::registerBlobURL(m_internalURL->url(), WTFMove(blobParts), contentType); > } > > Blob::Blob(ReferencingExistingBlobConstructor, ScriptExecutionContext* context, const Blob& blob) > : ActiveDOMObject(context) >- , m_internalURL(BlobURL::createInternalURL()) >+ , m_internalURL(BlobInternalURL::create()) > , m_type(blob.type()) > , m_size(blob.size()) > { >- ThreadableBlobRegistry::registerBlobURL(m_internalURL, { BlobPart(blob.url()) } , m_type); >+ ThreadableBlobRegistry::registerBlobURL(m_internalURL->url(), { BlobPart(blob.url()) } , m_type); > } > > Blob::Blob(DeserializationContructor, ScriptExecutionContext* context, const URL& srcURL, const String& type, std::optional<unsigned long long> size, const String& fileBackedPath) > : ActiveDOMObject(context) >+ , m_internalURL(BlobInternalURL::create()) > , m_type(normalizedContentType(type)) > , m_size(size) > { >- m_internalURL = BlobURL::createInternalURL(); > if (fileBackedPath.isEmpty()) >- ThreadableBlobRegistry::registerBlobURL(nullptr, m_internalURL, srcURL); >+ ThreadableBlobRegistry::registerBlobURL(nullptr, m_internalURL->url(), srcURL); > else >- ThreadableBlobRegistry::registerBlobURLOptionallyFileBacked(m_internalURL, srcURL, fileBackedPath, m_type); >+ ThreadableBlobRegistry::registerBlobURLOptionallyFileBacked(m_internalURL->url(), srcURL, fileBackedPath, m_type); > } > > Blob::Blob(ScriptExecutionContext* context, const URL& srcURL, long long start, long long end, const String& type) > : ActiveDOMObject(context) >+ , m_internalURL(BlobInternalURL::create()) > , m_type(normalizedContentType(type)) > // m_size is not necessarily equal to end - start so we do not initialize it here. > { >- m_internalURL = BlobURL::createInternalURL(); >- ThreadableBlobRegistry::registerBlobURLForSlice(m_internalURL, srcURL, start, end, m_type); >+ ThreadableBlobRegistry::registerBlobURLForSlice(m_internalURL->url(), srcURL, start, end, m_type); > } > > Blob::~Blob() > { > while (!m_blobLoaders.isEmpty()) > (*m_blobLoaders.begin())->cancel(); >+} > >- ThreadableBlobRegistry::unregisterBlobURL(m_internalURL); >+URL Blob::url() const >+{ >+ return m_internalURL->url(); >+} >+ >+Ref<Blob> Blob::slice(ScriptExecutionContext& context, long long start, long long end, const String& contentType) const >+{ >+ auto blob = adoptRef(*new Blob(&context, m_internalURL->url(), start, end, contentType)); >+ blob->suspendIfNeeded(); >+ return blob; > } > > unsigned long long Blob::size() const >@@ -162,7 +201,7 @@ unsigned long long Blob::size() const > if (!m_size) { > // FIXME: JavaScript cannot represent sizes as large as unsigned long long, we need to > // come up with an exception to throw if file size is not representable. >- unsigned long long actualSize = ThreadableBlobRegistry::blobSize(m_internalURL); >+ unsigned long long actualSize = ThreadableBlobRegistry::blobSize(m_internalURL->url()); > m_size = isInBounds<long long>(actualSize) ? actualSize : 0; > } > >@@ -335,5 +374,23 @@ const char* Blob::activeDOMObjectName() const > return "Blob"; > } > >+Blob::Handle Blob::handle() const >+{ >+ return Handle { m_internalURL.copyRef() }; >+} >+ >+Blob::Handle::Handle(Ref<BlobInternalURL>&& internalURL) >+ : m_internalURL(WTFMove(internalURL)) >+{ } >+ >+Blob::Handle::~Handle() = default; >+ >+Blob::Handle::Handle(Handle&&) = default; >+Blob::Handle::Handle(const Handle&) = default; >+ >+URL Blob::Handle::url() const >+{ >+ return m_internalURL->url(); >+} > > } // namespace WebCore >diff --git a/Source/WebCore/fileapi/Blob.h b/Source/WebCore/fileapi/Blob.h >index fd179e062116e2443de128435dedae873065ea44..cfde2c32fb07c519c46027d205a53d3fd14bf4bf 100644 >--- a/Source/WebCore/fileapi/Blob.h >+++ b/Source/WebCore/fileapi/Blob.h >@@ -57,6 +57,7 @@ class SharedBuffer; > template<typename> class ExceptionOr; > > using BlobPartVariant = Variant<RefPtr<JSC::ArrayBufferView>, RefPtr<JSC::ArrayBuffer>, RefPtr<Blob>, String>; >+class BlobInternalURL; > > class Blob : public ScriptWrappable, public URLRegistrable, public RefCounted<Blob>, public ActiveDOMObject { > WTF_MAKE_ISO_ALLOCATED_EXPORT(Blob, WEBCORE_EXPORT); >@@ -92,7 +93,7 @@ public: > > virtual ~Blob(); > >- const URL& url() const { return m_internalURL; } >+ WEBCORE_EXPORT URL url() const; > const String& type() const { return m_type; } > > WEBCORE_EXPORT unsigned long long size() const; >@@ -110,17 +111,26 @@ public: > // URLRegistrable > URLRegistry& registry() const override; > >- Ref<Blob> slice(ScriptExecutionContext& context, long long start, long long end, const String& contentType) const >- { >- auto blob = adoptRef(*new Blob(&context, m_internalURL, start, end, contentType)); >- blob->suspendIfNeeded(); >- return blob; >- } >+ Ref<Blob> slice(ScriptExecutionContext&, long long start, long long end, const String& contentType) const; > > void text(ScriptExecutionContext&, Ref<DeferredPromise>&&); > void arrayBuffer(ScriptExecutionContext&, Ref<DeferredPromise>&&); > ExceptionOr<Ref<ReadableStream>> stream(ScriptExecutionContext&); > >+ class Handle { >+ public: >+ explicit Handle(Ref<BlobInternalURL>&&); >+ ~Handle(); >+ Handle(Handle&&); >+ Handle(const Handle&); >+ URL url() const; >+ private: >+ Ref<BlobInternalURL> m_internalURL; >+ }; >+ >+ // Keeping the handle alive will keep the Blob data alive (but not the Blob object). >+ Handle handle() const; >+ > protected: > WEBCORE_EXPORT explicit Blob(ScriptExecutionContext*); > Blob(ScriptExecutionContext&, Vector<BlobPartVariant>&&, const BlobPropertyBag&); >@@ -147,7 +157,7 @@ private: > // This is an internal URL referring to the blob data associated with this object. It serves > // as an identifier for this blob. The internal URL is never used to source the blob's content > // into an HTML or for FileRead'ing, public blob URLs must be used for those purposes. >- URL m_internalURL; >+ Ref<BlobInternalURL> m_internalURL; > > String m_type; > >diff --git a/Source/WebCore/loader/EmptyClients.cpp b/Source/WebCore/loader/EmptyClients.cpp >index a3c98b1e3ca7ab76ee1f0a1b0e81a81ecd89ab17..8dca75b9407950789236d2aa120f43a7b3b1c6d7 100644 >--- a/Source/WebCore/loader/EmptyClients.cpp >+++ b/Source/WebCore/loader/EmptyClients.cpp >@@ -1175,7 +1175,7 @@ private: > > void registerChannel(const SecurityOriginData&, const String&, BroadcastChannelIdentifier) final { } > void unregisterChannel(const SecurityOriginData&, const String&, BroadcastChannelIdentifier) final { } >- void postMessage(const SecurityOriginData&, const String&, BroadcastChannelIdentifier, Ref<SerializedScriptValue>&&) final { } >+ void postMessage(const SecurityOriginData&, const String&, BroadcastChannelIdentifier, Ref<SerializedScriptValue>&&, CompletionHandler<void()>&&) final { } > }; > > PageConfiguration pageConfigurationWithEmptyClients(PAL::SessionID sessionID) >diff --git a/Source/WebKit/NetworkProcess/NetworkBroadcastChannelRegistry.cpp b/Source/WebKit/NetworkProcess/NetworkBroadcastChannelRegistry.cpp >index be88a53695b9b4db5e365f2521846a9bf0903c7f..9b86ebfc30343b4e454532f26c0ab281dfd35796 100644 >--- a/Source/WebKit/NetworkProcess/NetworkBroadcastChannelRegistry.cpp >+++ b/Source/WebKit/NetworkProcess/NetworkBroadcastChannelRegistry.cpp >@@ -28,6 +28,7 @@ > > #include "WebBroadcastChannelRegistryMessages.h" > #include <WebCore/MessageWithMessagePorts.h> >+#include <wtf/CallbackAggregator.h> > > namespace WebKit { > >@@ -58,23 +59,28 @@ void NetworkBroadcastChannelRegistry::unregisterChannel(IPC::Connection& connect > channelsForNameIterator->value.removeFirst(globalChannelIdentifier); > } > >-void NetworkBroadcastChannelRegistry::postMessage(IPC::Connection& connection, const WebCore::SecurityOriginData& origin, const String& name, WebCore::BroadcastChannelIdentifier source, WebCore::MessageWithMessagePorts&& message) >+void NetworkBroadcastChannelRegistry::postMessage(IPC::Connection& connection, const WebCore::SecurityOriginData& origin, const String& name, WebCore::BroadcastChannelIdentifier source, WebCore::MessageWithMessagePorts&& message, CompletionHandler<void()>&& completionHandler) > { > auto channelsForOriginIterator = m_broadcastChannels.find(origin); > ASSERT(channelsForOriginIterator != m_broadcastChannels.end()); > if (channelsForOriginIterator == m_broadcastChannels.end()) >- return; >+ return completionHandler(); > auto channelsForNameIterator = channelsForOriginIterator->value.find(name); > ASSERT(channelsForNameIterator != channelsForOriginIterator->value.end()); > if (channelsForNameIterator == channelsForOriginIterator->value.end()) >- return; >+ return completionHandler(); > >+ auto callbackAggregator = CallbackAggregator::create(WTFMove(completionHandler)); > GlobalBroadcastChannelIdentifier sourceGlobalChannelIdentifier { connection.uniqueID(), source }; > for (auto& globalIdentifier : channelsForNameIterator->value) { > if (globalIdentifier == sourceGlobalChannelIdentifier) > continue; > >- IPC::Connection::send(globalIdentifier.connectionIdentifier, Messages::WebBroadcastChannelRegistry::PostMessageToRemote(globalIdentifier.channelIndentifierInProcess, message), 0); >+ RefPtr connection = IPC::Connection::connection(globalIdentifier.connectionIdentifier); >+ if (!connection) >+ continue; >+ >+ connection->sendWithAsyncReply(Messages::WebBroadcastChannelRegistry::PostMessageToRemote(globalIdentifier.channelIndentifierInProcess, message), [callbackAggregator] { }, 0); > } > } > >diff --git a/Source/WebKit/NetworkProcess/NetworkBroadcastChannelRegistry.h b/Source/WebKit/NetworkProcess/NetworkBroadcastChannelRegistry.h >index 01b194618cd26840d557e2f57da7eab82564f309..415a6965b9a53c71deb0250148b450dfdb6f1fa8 100644 >--- a/Source/WebKit/NetworkProcess/NetworkBroadcastChannelRegistry.h >+++ b/Source/WebKit/NetworkProcess/NetworkBroadcastChannelRegistry.h >@@ -47,7 +47,7 @@ public: > > void registerChannel(IPC::Connection&, const WebCore::SecurityOriginData&, const String& name, WebCore::BroadcastChannelIdentifier); > void unregisterChannel(IPC::Connection&, const WebCore::SecurityOriginData&, const String& name, WebCore::BroadcastChannelIdentifier); >- void postMessage(IPC::Connection&, const WebCore::SecurityOriginData&, const String& name, WebCore::BroadcastChannelIdentifier source, WebCore::MessageWithMessagePorts&&); >+ void postMessage(IPC::Connection&, const WebCore::SecurityOriginData&, const String& name, WebCore::BroadcastChannelIdentifier source, WebCore::MessageWithMessagePorts&&, CompletionHandler<void()>&&); > > private: > struct GlobalBroadcastChannelIdentifier { >diff --git a/Source/WebKit/NetworkProcess/NetworkBroadcastChannelRegistry.messages.in b/Source/WebKit/NetworkProcess/NetworkBroadcastChannelRegistry.messages.in >index 1aa9c1bfa8a5f9ce0b4a94e1268aa38db3dd7971..9b6850b95583376e4991d215a2cdd715449afd9e 100644 >--- a/Source/WebKit/NetworkProcess/NetworkBroadcastChannelRegistry.messages.in >+++ b/Source/WebKit/NetworkProcess/NetworkBroadcastChannelRegistry.messages.in >@@ -23,5 +23,5 @@ > messages -> NetworkBroadcastChannelRegistry NotRefCounted { > RegisterChannel(struct WebCore::SecurityOriginData origin, String name, WebCore::BroadcastChannelIdentifier channelIdentifier) WantsConnection > UnregisterChannel(struct WebCore::SecurityOriginData origin, String name, WebCore::BroadcastChannelIdentifier channelIdentifier) WantsConnection >- PostMessage(struct WebCore::SecurityOriginData origin, String name, WebCore::BroadcastChannelIdentifier source, struct WebCore::MessageWithMessagePorts message) WantsConnection >+ PostMessage(struct WebCore::SecurityOriginData origin, String name, WebCore::BroadcastChannelIdentifier source, struct WebCore::MessageWithMessagePorts message) -> () Async WantsConnection > } >diff --git a/Source/WebKit/Platform/IPC/HandleMessage.h b/Source/WebKit/Platform/IPC/HandleMessage.h >index 2ab0fc26531c773f51d6d2d558684bda136bb6aa..989bb723f98d7dd2818a41ef61337fe69c3fcd5f 100644 >--- a/Source/WebKit/Platform/IPC/HandleMessage.h >+++ b/Source/WebKit/Platform/IPC/HandleMessage.h >@@ -200,15 +200,20 @@ void handleMessageAsync(Connection& connection, Decoder& decoder, C* object, MF > template<typename T, typename C, typename MF> > void handleMessageAsyncWantsConnection(Connection& connection, Decoder& decoder, C* object, MF function) > { >+ std::optional<uint64_t> listenerID; >+ decoder >> listenerID; >+ if (!listenerID) >+ return; >+ > std::optional<typename CodingType<typename T::Arguments>::Type> arguments; > decoder >> arguments; > if (UNLIKELY(!arguments)) > return; > >- typename T::AsyncReply completionHandler = [listenerID = decoder.destinationID(), connection = makeRef(connection)] (auto&&... args) mutable { >+ typename T::AsyncReply completionHandler = { [listenerID = *listenerID, connection = makeRef(connection)] (auto&&... args) mutable { > auto encoder = makeUniqueRef<Encoder>(T::asyncMessageReplyName(), listenerID); > T::send(WTFMove(encoder), WTFMove(connection), args...); >- }; >+ }, T::callbackThread }; > callMemberFunction(connection, WTFMove(*arguments), WTFMove(completionHandler), object, function); > } > >diff --git a/Source/WebKit/WebProcess/WebCoreSupport/WebBroadcastChannelRegistry.cpp b/Source/WebKit/WebProcess/WebCoreSupport/WebBroadcastChannelRegistry.cpp >index 789c163f6b5868cbcd87559a0eb97218a0456cd3..6dc7d6aba01e58cc3b1b1c8b9b02fb03df559920 100644 >--- a/Source/WebKit/WebProcess/WebCoreSupport/WebBroadcastChannelRegistry.cpp >+++ b/Source/WebKit/WebProcess/WebCoreSupport/WebBroadcastChannelRegistry.cpp >@@ -49,14 +49,14 @@ void WebBroadcastChannelRegistry::unregisterChannel(const WebCore::SecurityOrigi > networkProcessConnection().send(Messages::NetworkBroadcastChannelRegistry::UnregisterChannel { origin, name, identifier }, 0); > } > >-void WebBroadcastChannelRegistry::postMessage(const WebCore::SecurityOriginData& origin, const String& name, WebCore::BroadcastChannelIdentifier source, Ref<WebCore::SerializedScriptValue>&& message) >+void WebBroadcastChannelRegistry::postMessage(const WebCore::SecurityOriginData& origin, const String& name, WebCore::BroadcastChannelIdentifier source, Ref<WebCore::SerializedScriptValue>&& message, CompletionHandler<void()>&& completionHandler) > { >- networkProcessConnection().send(Messages::NetworkBroadcastChannelRegistry::PostMessage { origin, name, source, WebCore::MessageWithMessagePorts { WTFMove(message), { } } }, 0); >+ networkProcessConnection().sendWithAsyncReply(Messages::NetworkBroadcastChannelRegistry::PostMessage { origin, name, source, WebCore::MessageWithMessagePorts { WTFMove(message), { } } }, WTFMove(completionHandler), 0); > } > >-void WebBroadcastChannelRegistry::postMessageToRemote(WebCore::BroadcastChannelIdentifier identifier, WebCore::MessageWithMessagePorts&& message) >+void WebBroadcastChannelRegistry::postMessageToRemote(WebCore::BroadcastChannelIdentifier identifier, WebCore::MessageWithMessagePorts&& message, CompletionHandler<void()>&& completionHandler) > { >- WebCore::BroadcastChannel::dispatchMessageTo(identifier, message.message.releaseNonNull()); >+ WebCore::BroadcastChannel::dispatchMessageTo(identifier, message.message.releaseNonNull(), WTFMove(completionHandler)); > } > > } // namespace WebKit >diff --git a/Source/WebKit/WebProcess/WebCoreSupport/WebBroadcastChannelRegistry.h b/Source/WebKit/WebProcess/WebCoreSupport/WebBroadcastChannelRegistry.h >index 5d4f6c408a17bd2909d6c462d4d46891eecd11f4..44a3d382c08150f7a09a8e8e97fc286caac17c53 100644 >--- a/Source/WebKit/WebProcess/WebCoreSupport/WebBroadcastChannelRegistry.h >+++ b/Source/WebKit/WebProcess/WebCoreSupport/WebBroadcastChannelRegistry.h >@@ -43,14 +43,14 @@ public: > > void registerChannel(const WebCore::SecurityOriginData&, const String& name, WebCore::BroadcastChannelIdentifier) final; > void unregisterChannel(const WebCore::SecurityOriginData&, const String& name, WebCore::BroadcastChannelIdentifier) final; >- void postMessage(const WebCore::SecurityOriginData&, const String& name, WebCore::BroadcastChannelIdentifier source, Ref<WebCore::SerializedScriptValue>&&) final; >+ void postMessage(const WebCore::SecurityOriginData&, const String& name, WebCore::BroadcastChannelIdentifier source, Ref<WebCore::SerializedScriptValue>&&, CompletionHandler<void()>&&) final; > > void didReceiveMessage(IPC::Connection&, IPC::Decoder&); > > private: > WebBroadcastChannelRegistry() = default; > >- void postMessageToRemote(WebCore::BroadcastChannelIdentifier, WebCore::MessageWithMessagePorts&&); >+ void postMessageToRemote(WebCore::BroadcastChannelIdentifier, WebCore::MessageWithMessagePorts&&, CompletionHandler<void()>&&); > }; > > } // namespace WebKit >diff --git a/Source/WebKit/WebProcess/WebCoreSupport/WebBroadcastChannelRegistry.messages.in b/Source/WebKit/WebProcess/WebCoreSupport/WebBroadcastChannelRegistry.messages.in >index b04173affb46b17d31b397da1ebe741224cbe39d..07af52f8d8e48721a600de6d53c70448e32ecbfd 100644 >--- a/Source/WebKit/WebProcess/WebCoreSupport/WebBroadcastChannelRegistry.messages.in >+++ b/Source/WebKit/WebProcess/WebCoreSupport/WebBroadcastChannelRegistry.messages.in >@@ -21,5 +21,5 @@ > # OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. > > messages -> WebBroadcastChannelRegistry { >- PostMessageToRemote(WebCore::BroadcastChannelIdentifier destination, struct WebCore::MessageWithMessagePorts message) >+ PostMessageToRemote(WebCore::BroadcastChannelIdentifier destination, struct WebCore::MessageWithMessagePorts message) -> () Async > } >diff --git a/Source/WebKitLegacy/WebCoreSupport/WebBroadcastChannelRegistry.cpp b/Source/WebKitLegacy/WebCoreSupport/WebBroadcastChannelRegistry.cpp >index 1126e3a9308227579112abdd61dcdabc875b4936..45c32a1b38589b2bd3c89a738f7a982ae2c32811 100644 >--- a/Source/WebKitLegacy/WebCoreSupport/WebBroadcastChannelRegistry.cpp >+++ b/Source/WebKitLegacy/WebCoreSupport/WebBroadcastChannelRegistry.cpp >@@ -27,6 +27,7 @@ > > #include <WebCore/BroadcastChannel.h> > #include <WebCore/SerializedScriptValue.h> >+#include <wtf/CallbackAggregator.h> > #include <wtf/HashMap.h> > #include <wtf/NeverDestroyed.h> > >@@ -65,9 +66,11 @@ void WebBroadcastChannelRegistry::unregisterChannel(const WebCore::SecurityOrigi > channelsForNameIterator->value.removeFirst(identifier); > } > >-void WebBroadcastChannelRegistry::postMessage(const WebCore::SecurityOriginData& origin, const String& name, WebCore::BroadcastChannelIdentifier source, Ref<WebCore::SerializedScriptValue>&& message) >+void WebBroadcastChannelRegistry::postMessage(const WebCore::SecurityOriginData& origin, const String& name, WebCore::BroadcastChannelIdentifier source, Ref<WebCore::SerializedScriptValue>&& message, CompletionHandler<void()>&& completionHandler) > { > ASSERT(isMainThread()); >+ auto callbackAggregator = CallbackAggregator::create(WTFMove(completionHandler)); >+ > auto channelsForOriginIterator = m_channels.find(origin); > ASSERT(channelsForOriginIterator != m_channels.end()); > if (channelsForOriginIterator == m_channels.end()) >@@ -78,6 +81,6 @@ void WebBroadcastChannelRegistry::postMessage(const WebCore::SecurityOriginData& > for (auto& channelIdentifier : channelsForNameIterator->value) { > if (channelIdentifier == source) > continue; >- WebCore::BroadcastChannel::dispatchMessageTo(channelIdentifier, message.copyRef()); >+ WebCore::BroadcastChannel::dispatchMessageTo(channelIdentifier, message.copyRef(), [callbackAggregator] { }); > } > } >diff --git a/Source/WebKitLegacy/WebCoreSupport/WebBroadcastChannelRegistry.h b/Source/WebKitLegacy/WebCoreSupport/WebBroadcastChannelRegistry.h >index f5c7cf5518b8a681f4b8f5c830dec2e68bf18197..3711322051c7b81f6b21a5fb4c15c007063d9408 100644 >--- a/Source/WebKitLegacy/WebCoreSupport/WebBroadcastChannelRegistry.h >+++ b/Source/WebKitLegacy/WebCoreSupport/WebBroadcastChannelRegistry.h >@@ -36,7 +36,7 @@ public: > > void registerChannel(const WebCore::SecurityOriginData&, const String& name, WebCore::BroadcastChannelIdentifier) final; > void unregisterChannel(const WebCore::SecurityOriginData&, const String& name, WebCore::BroadcastChannelIdentifier) final; >- void postMessage(const WebCore::SecurityOriginData&, const String& name, WebCore::BroadcastChannelIdentifier source, Ref<WebCore::SerializedScriptValue>&&) final; >+ void postMessage(const WebCore::SecurityOriginData&, const String& name, WebCore::BroadcastChannelIdentifier source, Ref<WebCore::SerializedScriptValue>&&, CompletionHandler<void()>&&) final; > > private: > WebBroadcastChannelRegistry() = default; >diff --git a/LayoutTests/ChangeLog b/LayoutTests/ChangeLog >index 17c338f1fcb8c388d40c86e34d8d5c387f99a3ca..324c457cbd9edff0546311ca1f4f9bba26014c4d 100644 >--- a/LayoutTests/ChangeLog >+++ b/LayoutTests/ChangeLog >@@ -1,3 +1,16 @@ >+2021-07-29 Chris Dumez <cdumez@apple.com> >+ >+ imported/w3c/web-platform-tests/webmessaging/broadcastchannel/blobs.html is a flaky failure since implementing BlobChannel >+ https://bugs.webkit.org/show_bug.cgi?id=228168 >+ <rdar://problem/80922502> >+ >+ Reviewed by NOBODY (OOPS!). >+ >+ Unskip test that is no longer flaky. >+ >+ * platform/ios-wk2/TestExpectations: >+ * platform/mac/TestExpectations: >+ > 2021-07-29 Chris Dumez <cdumez@apple.com> > > Unreviewed, unskip storage/indexeddb/detached-iframe.html now that it is no longer flaky after r280426. >diff --git a/LayoutTests/platform/ios-wk2/TestExpectations b/LayoutTests/platform/ios-wk2/TestExpectations >index 739d48e01bd857c4a574d55e46d6291306cb3fd2..64fffb403ba1bcc7b93c6d2fb1a35639c27feb9a 100644 >--- a/LayoutTests/platform/ios-wk2/TestExpectations >+++ b/LayoutTests/platform/ios-wk2/TestExpectations >@@ -1991,8 +1991,6 @@ webkit.org/b/228114 imported/w3c/web-platform-tests/fetch/content-type/script.wi > > webkit.org/b/228127 imported/w3c/web-platform-tests/html/cross-origin-opener-policy/resource-popup.https.html [ Pass Failure ] > >-webkit.org/b/228168 imported/w3c/web-platform-tests/webmessaging/broadcastchannel/blobs.html [ Pass Failure ] >- > webkit.org/b/227998 imported/w3c/web-platform-tests/html/semantics/embedded-content/the-embed-element/embed-network-error.sub.html [ Pass Failure ] > > webkit.org/b/227762 [ Debug ] imported/w3c/web-platform-tests/html/interaction/focus/the-autofocus-attribute/document-with-fragment-valid.html [ Pass Failure ] >diff --git a/LayoutTests/platform/mac/TestExpectations b/LayoutTests/platform/mac/TestExpectations >index 72a1b97ce87352bce8e0605120e05547a0748187..729fcdada89fd05151ce528caa67dc58d8e1e700 100644 >--- a/LayoutTests/platform/mac/TestExpectations >+++ b/LayoutTests/platform/mac/TestExpectations >@@ -2345,8 +2345,6 @@ webkit.org/b/214574 svg/animations/smil-leak-list-property-instances.svg [ Pass > > webkit.org/b/228127 imported/w3c/web-platform-tests/html/cross-origin-opener-policy/resource-popup.https.html [ Pass Failure ] > >-webkit.org/b/228168 imported/w3c/web-platform-tests/webmessaging/broadcastchannel/blobs.html [ Pass Failure ] >- > webkit.org/b/222385 imported/w3c/web-platform-tests/xhr/event-upload-progress-crossorigin.any.worker.html [ Pass Failure ] > > webkit.org/b/227998 imported/w3c/web-platform-tests/html/semantics/embedded-content/the-embed-element/embed-network-error.sub.html [ Pass Failure ]
You cannot view the attachment while viewing its details because your browser does not support IFRAMEs.
View the attachment on a separate page
.
View Attachment As Diff
View Attachment As Raw
Actions:
View
|
Formatted Diff
|
Diff
Attachments on
bug 228168
:
434561
|
434662
|
434675