Diff
Modified: trunk/Source/WebKit/ChangeLog (286074 => 286075)
--- trunk/Source/WebKit/ChangeLog 2021-11-19 21:35:00 UTC (rev 286074)
+++ trunk/Source/WebKit/ChangeLog 2021-11-19 21:43:17 UTC (rev 286075)
@@ -1,3 +1,66 @@
+2021-11-19 Brady Eidson <beid...@apple.com>
+
+ More webpushd architecture work
+ https://bugs.webkit.org/show_bug.cgi?id=233295
+
+ Reviewed by Alex Christensen.
+
+ Covered by API tests.
+
+ This patch:
+ - Adds entitlement checks for connections to webpushd
+ - Adds a "ClientConnection" object to the daemon to manage per-connection state
+ - Adds a debug enabled setting
+ - Adds the ability for the connecting app (com.apple.WebKit.Networking) to pass the host app's audit_token
+ - Tests some of the above
+ - Adds the beginnings of other future infrastructure
+
+ * NetworkProcess/Notifications/NetworkNotificationManager.cpp:
+ (WebKit::NetworkNotificationManager::NetworkNotificationManager):
+
+ * Resources/ios/XPCService-embedded-simulator.entitlements:
+ * Scripts/process-entitlements.sh:
+
+ * Shared/Cocoa/CodeSigning.h:
+ * Shared/Cocoa/CodeSigning.mm:
+ (WebKit::codeSigningIdentifierAndPlatformBinaryStatus):
+ (WebKit::codeSigningIdentifier):
+
+ * Shared/WebPushDaemonConstants.h:
+ (WebKit::WebPushD::messageTypeSendsReply):
+
+ * WebKit.xcodeproj/project.pbxproj:
+
+ * webpushd/PushClientConnection.h: Copied from Source/WebKit/Shared/Cocoa/CodeSigning.h.
+ (WebPushD::ClientConnection::hasAuditToken const):
+ (WebPushD::ClientConnection::debugModeIsEnabled const):
+ * webpushd/PushClientConnection.mm: Added.
+ (WebPushD::ClientConnection::ClientConnection):
+ (WebPushD::ClientConnection::setAuditTokenData):
+ (WebPushD::ClientConnection::hostCodeSigningIdentifier):
+ (WebPushD::ClientConnection::hostHasPushEntitlement):
+ (WebPushD::ClientConnection::setDebugModeIsEnabled):
+
+ * webpushd/WebPushDaemon.h:
+ * webpushd/WebPushDaemon.mm:
+ (WebPushD::handleWebPushDMessageWithReply):
+ (WebPushD::handleWebPushDMessage):
+ (WebPushD::Daemon::broadcastDebugMessage):
+ (WebPushD::Daemon::connectionEventHandler):
+ (WebPushD::Daemon::connectionAdded):
+ (WebPushD::Daemon::connectionRemoved):
+ (WebPushD::Daemon::decodeAndHandleMessage):
+ (WebPushD::Daemon::echoTwice):
+ (WebPushD::Daemon::canRegisterForNotifications):
+ (WebPushD::Daemon::requestSystemNotificationPermission):
+ (WebPushD::Daemon::getOriginsWithPushAndNotificationPermissions):
+ (WebPushD::Daemon::deletePushAndNotificationRegistration):
+ (WebPushD::Daemon::setHostAppAuditToken):
+ (WebPushD::Daemon::setDebugModeIsEnabled):
+ (WebPushD::Daemon::toClientConnection):
+ * webpushd/WebPushDaemonMain.mm:
+ (main):
+
2021-11-19 Brent Fulgham <bfulg...@apple.com>
Add support for web app manifest icons in WebKit/UI Process layer
Modified: trunk/Source/WebKit/NetworkProcess/Notifications/NetworkNotificationManager.cpp (286074 => 286075)
--- trunk/Source/WebKit/NetworkProcess/Notifications/NetworkNotificationManager.cpp 2021-11-19 21:35:00 UTC (rev 286074)
+++ trunk/Source/WebKit/NetworkProcess/Notifications/NetworkNotificationManager.cpp 2021-11-19 21:43:17 UTC (rev 286075)
@@ -43,6 +43,25 @@
m_connection = makeUnique<WebPushD::Connection>(webPushMachServiceName.utf8(), *this);
}
+void NetworkNotificationManager::maybeSendHostAppAuditToken() const
+{
+ if (m_sentHostAppAuditToken)
+ return;
+ m_sentHostAppAuditToken = true;
+
+#if PLATFORM(COCOA)
+ auto token = m_networkSession.networkProcess().parentProcessConnection()->getAuditToken();
+ if (!token)
+ return;
+
+ Vector<uint8_t> auditTokenData;
+ auditTokenData.resize(sizeof(*token));
+ memcpy(auditTokenData.data(), &(*token), sizeof(*token));
+
+ sendMessage<WebPushD::MessageType::SetHostAppAuditToken>(auditTokenData);
+#endif
+}
+
void NetworkNotificationManager::requestSystemNotificationPermission(const String& originString, CompletionHandler<void(bool)>&& completionHandler)
{
sendMessageWithReply<WebPushD::MessageType::RequestSystemNotificationPermission>(WTFMove(completionHandler), originString);
@@ -103,6 +122,9 @@
void NetworkNotificationManager::sendMessage(Args&&... args) const
{
RELEASE_ASSERT(m_connection);
+
+ maybeSendHostAppAuditToken();
+
Daemon::Encoder encoder;
encoder.encode(std::forward<Args>(args)...);
m_connection->send(messageType, encoder.takeBuffer());
@@ -165,6 +187,8 @@
{
RELEASE_ASSERT(m_connection);
+ maybeSendHostAppAuditToken();
+
Daemon::Encoder encoder;
encoder.encode(std::forward<Args>(args)...);
m_connection->sendWithReply(messageType, encoder.takeBuffer(), [completionHandler = WTFMove(completionHandler)] (auto replyBuffer) mutable {
Modified: trunk/Source/WebKit/NetworkProcess/Notifications/NetworkNotificationManager.h (286074 => 286075)
--- trunk/Source/WebKit/NetworkProcess/Notifications/NetworkNotificationManager.h 2021-11-19 21:35:00 UTC (rev 286074)
+++ trunk/Source/WebKit/NetworkProcess/Notifications/NetworkNotificationManager.h 2021-11-19 21:43:17 UTC (rev 286075)
@@ -62,8 +62,11 @@
void clearNotifications(const Vector<uint64_t>& notificationIDs) final;
void didDestroyNotification(uint64_t notificationID) final;
+ void maybeSendHostAppAuditToken() const;
+
NetworkSession& m_networkSession;
std::unique_ptr<WebPushD::Connection> m_connection;
+ mutable bool m_sentHostAppAuditToken { false };
template<WebPushD::MessageType messageType, typename... Args>
void sendMessage(Args&&...) const;
Modified: trunk/Source/WebKit/Resources/ios/XPCService-embedded-simulator.entitlements (286074 => 286075)
--- trunk/Source/WebKit/Resources/ios/XPCService-embedded-simulator.entitlements 2021-11-19 21:35:00 UTC (rev 286074)
+++ trunk/Source/WebKit/Resources/ios/XPCService-embedded-simulator.entitlements 2021-11-19 21:43:17 UTC (rev 286075)
@@ -6,5 +6,7 @@
<true/>
<key>com.apple.private.webkit.use-xpc-endpoint</key>
<true/>
+ <key>com.apple.private.webkit.webpush</key>
+ <true/>
</dict>
</plist>
Modified: trunk/Source/WebKit/Scripts/process-entitlements.sh (286074 => 286075)
--- trunk/Source/WebKit/Scripts/process-entitlements.sh 2021-11-19 21:35:00 UTC (rev 286074)
+++ trunk/Source/WebKit/Scripts/process-entitlements.sh 2021-11-19 21:43:17 UTC (rev 286075)
@@ -131,6 +131,7 @@
plistbuddy Add :com.apple.rootless.storage.WebKitNetworkingSandbox bool YES
plistbuddy Add :com.apple.symptom_analytics.configure bool YES
plistbuddy Add :com.apple.private.webkit.adattributiond bool YES
+ plistbuddy Add :com.apple.private.webkit.webpush bool YES
fi
}
@@ -401,6 +402,7 @@
function ios_family_process_network_entitlements()
{
plistbuddy Add :com.apple.private.webkit.adattributiond bool YES
+ plistbuddy Add :com.apple.private.webkit.webpush bool YES
plistbuddy Add :com.apple.multitasking.systemappassertions bool YES
plistbuddy Add :com.apple.payment.all-access bool YES
plistbuddy Add :com.apple.private.accounts.bundleidspoofing bool YES
Modified: trunk/Source/WebKit/Shared/Cocoa/CodeSigning.h (286074 => 286075)
--- trunk/Source/WebKit/Shared/Cocoa/CodeSigning.h 2021-11-19 21:35:00 UTC (rev 286074)
+++ trunk/Source/WebKit/Shared/Cocoa/CodeSigning.h 2021-11-19 21:43:17 UTC (rev 286075)
@@ -33,6 +33,7 @@
// These functions return a null string if the process is unsigned.
String codeSigningIdentifierForCurrentProcess();
String codeSigningIdentifier(xpc_connection_t);
+String codeSigningIdentifier(audit_token_t);
bool currentProcessIsPlatformBinary();
std::pair<String, bool> codeSigningIdentifierAndPlatformBinaryStatus(xpc_connection_t);
Modified: trunk/Source/WebKit/Shared/Cocoa/CodeSigning.mm (286074 => 286075)
--- trunk/Source/WebKit/Shared/Cocoa/CodeSigning.mm 2021-11-19 21:35:00 UTC (rev 286074)
+++ trunk/Source/WebKit/Shared/Cocoa/CodeSigning.mm 2021-11-19 21:43:17 UTC (rev 286075)
@@ -57,10 +57,8 @@
return SecTaskGetCodeSignStatus(task.get()) & CS_PLATFORM_BINARY;
}
-std::pair<String, bool> codeSigningIdentifierAndPlatformBinaryStatus(xpc_connection_t connection)
+static std::pair<String, bool> codeSigningIdentifierAndPlatformBinaryStatus(audit_token_t auditToken)
{
- audit_token_t auditToken;
- xpc_connection_get_audit_token(connection, &auditToken);
auto task = adoptCF(SecTaskCreateWithAuditToken(kCFAllocatorDefault, auditToken));
bool isPlatformBinary = SecTaskGetCodeSignStatus(task.get()) & CS_PLATFORM_BINARY;
auto signingIdentifier = codeSigningIdentifier(task.get());
@@ -67,6 +65,20 @@
return std::make_pair(signingIdentifier, isPlatformBinary);
}
+std::pair<String, bool> codeSigningIdentifierAndPlatformBinaryStatus(xpc_connection_t connection)
+{
+ audit_token_t auditToken;
+ xpc_connection_get_audit_token(connection, &auditToken);
+
+ return codeSigningIdentifierAndPlatformBinaryStatus(auditToken);
+}
+
+String codeSigningIdentifier(audit_token_t token)
+{
+ auto pair = codeSigningIdentifierAndPlatformBinaryStatus(token);
+ return pair.first;
+}
+
} // namespace WebKit
#endif // PLATFORM(COCOA)
Modified: trunk/Source/WebKit/Shared/WebPushDaemonConstants.h (286074 => 286075)
--- trunk/Source/WebKit/Shared/WebPushDaemonConstants.h 2021-11-19 21:35:00 UTC (rev 286074)
+++ trunk/Source/WebKit/Shared/WebPushDaemonConstants.h 2021-11-19 21:43:17 UTC (rev 286075)
@@ -40,6 +40,8 @@
RequestSystemNotificationPermission,
DeletePushAndNotificationRegistration,
GetOriginsWithPushAndNotificationPermissions,
+ SetHostAppAuditToken,
+ SetDebugModeIsEnabled,
};
inline bool messageTypeSendsReply(MessageType messageType)
@@ -50,6 +52,9 @@
case MessageType::DeletePushAndNotificationRegistration:
case MessageType::RequestSystemNotificationPermission:
return true;
+ case MessageType::SetHostAppAuditToken:
+ case MessageType::SetDebugModeIsEnabled:
+ return false;
}
ASSERT_NOT_REACHED();
return false;
Modified: trunk/Source/WebKit/WebKit.xcodeproj/project.pbxproj (286074 => 286075)
--- trunk/Source/WebKit/WebKit.xcodeproj/project.pbxproj 2021-11-19 21:35:00 UTC (rev 286074)
+++ trunk/Source/WebKit/WebKit.xcodeproj/project.pbxproj 2021-11-19 21:43:17 UTC (rev 286075)
@@ -1047,6 +1047,10 @@
51F060E11654318500F3282E /* NetworkRTCProviderMessageReceiver.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 51F060DD1654317500F3282E /* NetworkRTCProviderMessageReceiver.cpp */; };
51F060E11654318500F3282F /* WebMDNSRegisterMessageReceiver.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 51F060DD1654317500F3282F /* WebMDNSRegisterMessageReceiver.cpp */; };
51F060E11654318500F3283F /* NetworkMDNSRegisterMessageReceiver.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 51F060DD1654317500F3283F /* NetworkMDNSRegisterMessageReceiver.cpp */; };
+ 51F7BB7B2744C50700C45A72 /* PushClientConnection.h in Headers */ = {isa = PBXBuildFile; fileRef = 51F7BB792744C50700C45A72 /* PushClientConnection.h */; };
+ 51F7BB7C2744C50700C45A72 /* PushClientConnection.mm in Sources */ = {isa = PBXBuildFile; fileRef = 51F7BB7A2744C50700C45A72 /* PushClientConnection.mm */; };
+ 51F7BB7D2745640400C45A72 /* CodeSigning.mm in Sources */ = {isa = PBXBuildFile; fileRef = CE11AD4F1CBC47F800681EE5 /* CodeSigning.mm */; };
+ 51F7BB7F274564A100C45A72 /* Security.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 51F7BB7E274564A100C45A72 /* Security.framework */; };
51F886A61F2C228100C193EF /* WKTestingSupport.h in Headers */ = {isa = PBXBuildFile; fileRef = 51F886A41F2C214A00C193EF /* WKTestingSupport.h */; settings = {ATTRIBUTES = (Private, ); }; };
51FAEC3A1B0657630009C4E7 /* AuxiliaryProcessMessages.h in Headers */ = {isa = PBXBuildFile; fileRef = 51FAEC371B0657310009C4E7 /* AuxiliaryProcessMessages.h */; };
51FAEC3B1B0657680009C4E7 /* AuxiliaryProcessMessageReceiver.cpp in Sources */ = {isa = PBXBuildFile; fileRef = 51FAEC361B0657310009C4E7 /* AuxiliaryProcessMessageReceiver.cpp */; };
@@ -4255,6 +4259,9 @@
51F060DD1654317500F3282F /* WebMDNSRegisterMessageReceiver.cpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; name = WebMDNSRegisterMessageReceiver.cpp; path = DerivedSources/WebKit2/WebMDNSRegisterMessageReceiver.cpp; sourceTree = BUILT_PRODUCTS_DIR; };
51F060DD1654317500F3283F /* NetworkMDNSRegisterMessageReceiver.cpp */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.cpp.cpp; name = NetworkMDNSRegisterMessageReceiver.cpp; path = DerivedSources/WebKit2/NetworkMDNSRegisterMessageReceiver.cpp; sourceTree = BUILT_PRODUCTS_DIR; };
51F060DE1654317500F3281B /* WebResourceLoaderMessages.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; name = WebResourceLoaderMessages.h; path = DerivedSources/WebKit2/WebResourceLoaderMessages.h; sourceTree = BUILT_PRODUCTS_DIR; };
+ 51F7BB792744C50700C45A72 /* PushClientConnection.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = PushClientConnection.h; sourceTree = "<group>"; };
+ 51F7BB7A2744C50700C45A72 /* PushClientConnection.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = PushClientConnection.mm; sourceTree = "<group>"; };
+ 51F7BB7E274564A100C45A72 /* Security.framework */ = {isa = PBXFileReference; lastKnownFileType = wrapper.framework; name = Security.framework; path = System/Library/Frameworks/Security.framework; sourceTree = SDKROOT; };
51F886A31F2C214A00C193EF /* WKTestingSupport.cpp */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.cpp; path = WKTestingSupport.cpp; sourceTree = "<group>"; };
51F886A41F2C214A00C193EF /* WKTestingSupport.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = WKTestingSupport.h; sourceTree = "<group>"; };
51FA2D541521118600C1BA0B /* WKBundleDOMWindowExtension.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = WKBundleDOMWindowExtension.h; sourceTree = "<group>"; };
@@ -6229,6 +6236,7 @@
isa = PBXFrameworksBuildPhase;
buildActionMask = 2147483647;
files = (
+ 51F7BB7F274564A100C45A72 /* Security.framework in Frameworks */,
);
runOnlyForDeploymentPostprocessing = 0;
};
@@ -9345,6 +9353,7 @@
5750F3292032D4E300389347 /* Frameworks */ = {
isa = PBXGroup;
children = (
+ 51F7BB7E274564A100C45A72 /* Security.framework */,
57A9FF15252C6AEF006A2040 /* libWTF.a */,
5750F32A2032D4E500389347 /* LocalAuthentication.framework */,
570DAAB0230273D200E8FC04 /* NearField.framework */,
@@ -9595,6 +9604,8 @@
isa = PBXGroup;
children = (
5CBB6D4D271F67CC00FD1A5D /* com.apple.webkit.webpushd.plist */,
+ 51F7BB792744C50700C45A72 /* PushClientConnection.h */,
+ 51F7BB7A2744C50700C45A72 /* PushClientConnection.mm */,
512CD69D2723393A00F7F8EC /* WebPushDaemon.h */,
512CD69E2723393A00F7F8EC /* WebPushDaemon.mm */,
5C157A0B2717CA1C00ED5280 /* WebPushDaemonMain.mm */,
@@ -12068,6 +12079,7 @@
isa = PBXHeadersBuildPhase;
buildActionMask = 2147483647;
files = (
+ 51F7BB7B2744C50700C45A72 /* PushClientConnection.h in Headers */,
5C1579FC2717AF5000ED5280 /* DaemonUtilities.h in Headers */,
512CD69F2723393A00F7F8EC /* WebPushDaemon.h in Headers */,
);
@@ -14546,8 +14558,10 @@
isa = PBXSourcesBuildPhase;
buildActionMask = 2147483647;
files = (
+ 51F7BB7D2745640400C45A72 /* CodeSigning.mm in Sources */,
5C157A012717B7FB00ED5280 /* ArgumentCoders.cpp in Sources */,
5C1579FF2717B6D200ED5280 /* DaemonDecoder.cpp in Sources */,
+ 51F7BB7C2744C50700C45A72 /* PushClientConnection.mm in Sources */,
5C1579FE2717B6C100ED5280 /* DaemonEncoder.cpp in Sources */,
5C1579FB2717AF5000ED5280 /* DaemonUtilities.mm in Sources */,
512CD6A02723393A00F7F8EC /* WebPushDaemon.mm in Sources */,
Copied: trunk/Source/WebKit/webpushd/PushClientConnection.h (from rev 286074, trunk/Source/WebKit/Shared/Cocoa/CodeSigning.h) (0 => 286075)
--- trunk/Source/WebKit/webpushd/PushClientConnection.h (rev 0)
+++ trunk/Source/WebKit/webpushd/PushClientConnection.h 2021-11-19 21:43:17 UTC (rev 286075)
@@ -0,0 +1,60 @@
+/*
+ * Copyright (C) 2021 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#pragma once
+
+#include <optional>
+#include <wtf/Forward.h>
+#include <wtf/OSObjectPtr.h>
+#include <wtf/spi/darwin/XPCSPI.h>
+#include <wtf/text/WTFString.h>
+
+namespace WebPushD {
+
+class ClientConnection {
+ WTF_MAKE_FAST_ALLOCATED;
+public:
+ ClientConnection(xpc_connection_t);
+
+ bool hasHostAppAuditToken() const { return !!m_hostAppAuditToken; }
+ void setHostAppAuditTokenData(const Vector<uint8_t>&);
+
+ const String& hostAppCodeSigningIdentifier();
+ bool hostAppHasPushEntitlement();
+
+ bool debugModeIsEnabled() const { return m_debugModeEnabled; }
+ void setDebugModeIsEnabled(bool);
+
+private:
+ OSObjectPtr<xpc_connection_t> m_xpcConnection;
+
+ std::optional<audit_token_t> m_hostAppAuditToken;
+ std::optional<String> m_hostAppCodeSigningIdentifier;
+ std::optional<bool> m_hostAppHasPushEntitlement;
+
+ bool m_debugModeEnabled { false };
+};
+
+} // namespace WebPushD
Added: trunk/Source/WebKit/webpushd/PushClientConnection.mm (0 => 286075)
--- trunk/Source/WebKit/webpushd/PushClientConnection.mm (rev 0)
+++ trunk/Source/WebKit/webpushd/PushClientConnection.mm 2021-11-19 21:43:17 UTC (rev 286075)
@@ -0,0 +1,96 @@
+/*
+ * Copyright (C) 2021 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS''
+ * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO,
+ * THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS
+ * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
+ * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
+ * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
+ * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
+ * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
+ * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF
+ * THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "config.h"
+#import "PushClientConnection.h"
+
+#import "CodeSigning.h"
+#import "WebPushDaemon.h"
+#import <_javascript_Core/ConsoleTypes.h>
+#import <wtf/Vector.h>
+#import <wtf/cocoa/Entitlements.h>
+
+namespace WebPushD {
+
+ClientConnection::ClientConnection(xpc_connection_t connection)
+ : m_xpcConnection(connection)
+{
+}
+
+void ClientConnection::setHostAppAuditTokenData(const Vector<uint8_t>& tokenData)
+{
+ RELEASE_ASSERT(!hasHostAppAuditToken());
+
+ audit_token_t token;
+ if (tokenData.size() != sizeof(token)) {
+ ASSERT_WITH_MESSAGE(false, "Attempt to set an audit token from incorrect number of bytes");
+ return;
+ }
+
+ memcpy(&token, tokenData.data(), tokenData.size());
+ m_hostAppAuditToken = WTFMove(token);
+}
+
+const String& ClientConnection::hostAppCodeSigningIdentifier()
+{
+ if (!m_hostAppCodeSigningIdentifier) {
+ if (!m_hostAppAuditToken)
+ m_hostAppCodeSigningIdentifier = String();
+ else
+ m_hostAppCodeSigningIdentifier = WebKit::codeSigningIdentifier(*m_hostAppAuditToken);
+ }
+
+ return *m_hostAppCodeSigningIdentifier;
+}
+
+bool ClientConnection::hostAppHasPushEntitlement()
+{
+ if (!m_hostAppHasPushEntitlement) {
+ if (!m_hostAppAuditToken)
+ return false;
+ m_hostAppHasPushEntitlement = WTF::hasEntitlement(*m_hostAppAuditToken, "com.apple.private.webkit.webpush");
+ }
+
+ return *m_hostAppHasPushEntitlement;
+}
+
+void ClientConnection::setDebugModeIsEnabled(bool enabled)
+{
+ if (enabled == m_debugModeEnabled)
+ return;
+
+ m_debugModeEnabled = enabled;
+
+ auto identifier = hostAppCodeSigningIdentifier();
+ String message;
+ if (!identifier.isEmpty())
+ message = makeString("[webpushd - ", identifier, "] Turned Debug Mode ", m_debugModeEnabled ? "on" : "off");
+ else
+ message = makeString("[webpushd] Turned Debug Mode ", m_debugModeEnabled ? "on" : "off");
+
+ Daemon::singleton().broadcastDebugMessage(MessageLevel::Info, message);
+}
+
+} // namespace WebPushD
Modified: trunk/Source/WebKit/webpushd/WebPushDaemon.h (286074 => 286075)
--- trunk/Source/WebKit/webpushd/WebPushDaemon.h 2021-11-19 21:35:00 UTC (rev 286074)
+++ trunk/Source/WebKit/webpushd/WebPushDaemon.h 2021-11-19 21:43:17 UTC (rev 286075)
@@ -25,15 +25,20 @@
#pragma once
+#include "PushClientConnection.h"
#include "WebPushDaemonConstants.h"
#include <wtf/Forward.h>
+#include <wtf/HashMap.h>
#include <wtf/HashSet.h>
#include <wtf/OSObjectPtr.h>
#include <wtf/Span.h>
#include <wtf/spi/darwin/XPCSPI.h>
-using WebKit::WebPushD::MessageType;
+namespace JSC {
+enum class MessageLevel : uint8_t;
+}
+
namespace WebPushD {
using EncodedMessage = Vector<uint8_t>;
@@ -48,18 +53,28 @@
void connectionRemoved(xpc_connection_t);
// Message handlers
- void echoTwice(const String&, CompletionHandler<void(const String&)>&& replySender);
- void requestSystemNotificationPermission(const String&, CompletionHandler<void(bool)>&& replySender);
- void getOriginsWithPushAndNotificationPermissions(CompletionHandler<void(const Vector<String>&)>&& replySender);
- void deletePushAndNotificationRegistration(const String& originString, CompletionHandler<void(const String&)>&& replySender);
+ void echoTwice(ClientConnection*, const String&, CompletionHandler<void(const String&)>&& replySender);
+ void requestSystemNotificationPermission(ClientConnection*, const String&, CompletionHandler<void(bool)>&& replySender);
+ void getOriginsWithPushAndNotificationPermissions(ClientConnection*, CompletionHandler<void(const Vector<String>&)>&& replySender);
+ void deletePushAndNotificationRegistration(ClientConnection*, const String& originString, CompletionHandler<void(const String&)>&& replySender);
+ void setHostAppAuditToken(ClientConnection*, const Vector<uint8_t>&);
+ void setDebugModeIsEnabled(ClientConnection*, bool);
+ void broadcastDebugMessage(JSC::MessageLevel, const String&);
+
private:
Daemon() = default;
- CompletionHandler<void(EncodedMessage&&)> createReplySender(MessageType, OSObjectPtr<xpc_object_t>&& request);
- void decodeAndHandleMessage(MessageType, Span<const uint8_t> encodedMessage, CompletionHandler<void(EncodedMessage&&)>&&);
+ CompletionHandler<void(EncodedMessage&&)> createReplySender(WebKit::WebPushD::MessageType, OSObjectPtr<xpc_object_t>&& request);
+ void decodeAndHandleMessage(xpc_connection_t, WebKit::WebPushD::MessageType, Span<const uint8_t> encodedMessage, CompletionHandler<void(EncodedMessage&&)>&&);
+ bool canRegisterForNotifications(ClientConnection&);
+
+ ClientConnection* toClientConnection(xpc_connection_t);
+
HashSet<String> m_inMemoryOriginStringsWithPermissionForTesting;
+
+ HashMap<xpc_connection_t, std::unique_ptr<ClientConnection>> m_connectionMap;
};
} // namespace WebPushD
Modified: trunk/Source/WebKit/webpushd/WebPushDaemon.mm (286074 => 286075)
--- trunk/Source/WebKit/webpushd/WebPushDaemon.mm 2021-11-19 21:35:00 UTC (rev 286074)
+++ trunk/Source/WebKit/webpushd/WebPushDaemon.mm 2021-11-19 21:43:17 UTC (rev 286075)
@@ -68,6 +68,14 @@
REPLY(bool)
END
+FUNCTION(setHostAppAuditToken)
+ARGUMENTS(Vector<uint8_t>)
+END
+
+FUNCTION(setDebugModeIsEnabled)
+ARGUMENTS(bool)
+END
+
#undef FUNCTION
#undef ARGUMENTS
#undef REPLY
@@ -104,7 +112,7 @@
} // namespace MessageInfo
template<typename Info>
-void handleWebPushDMessageWithReply(Span<const uint8_t> encodedMessage, CompletionHandler<void(WebPushD::EncodedMessage&&)>&& replySender)
+void handleWebPushDMessageWithReply(ClientConnection* connection, Span<const uint8_t> encodedMessage, CompletionHandler<void(WebPushD::EncodedMessage&&)>&& replySender)
{
WebKit::Daemon::Decoder decoder(encodedMessage);
@@ -117,9 +125,22 @@
replySender(Info::encodeReply(args...));
} };
- IPC::callMemberFunction(WTFMove(*arguments), WTFMove(completionHandler), &WebPushD::Daemon::singleton(), Info::MemberFunction);
+ IPC::callMemberFunction(tuple_cat(std::make_tuple(connection), WTFMove(*arguments)), WTFMove(completionHandler), &WebPushD::Daemon::singleton(), Info::MemberFunction);
}
+template<typename Info>
+void handleWebPushDMessage(ClientConnection* connection, Span<const uint8_t> encodedMessage)
+{
+ WebKit::Daemon::Decoder decoder(encodedMessage);
+
+ std::optional<typename Info::ArgsTuple> arguments;
+ decoder >> arguments;
+ if (UNLIKELY(!arguments))
+ return;
+
+ IPC::callMemberFunction(tuple_cat(std::make_tuple(connection), WTFMove(*arguments)), &WebPushD::Daemon::singleton(), Info::MemberFunction);
+}
+
Daemon& Daemon::singleton()
{
static NeverDestroyed<Daemon> daemon;
@@ -126,6 +147,17 @@
return daemon;
}
+void Daemon::broadcastDebugMessage(JSC::MessageLevel messageLevel, const String& message)
+{
+ auto dictionary = adoptOSObject(xpc_dictionary_create(nullptr, nullptr, 0));
+ xpc_dictionary_set_uint64(dictionary.get(), protocolDebugMessageLevelKey, static_cast<uint64_t>(messageLevel));
+ xpc_dictionary_set_string(dictionary.get(), protocolDebugMessageKey, message.utf8().data());
+ for (auto& iterator : m_connectionMap) {
+ if (iterator.value->debugModeIsEnabled())
+ xpc_connection_send_message(iterator.key, dictionary.get());
+ }
+}
+
void Daemon::connectionEventHandler(xpc_object_t request)
{
if (xpc_get_type(request) != XPC_TYPE_DICTIONARY)
@@ -142,17 +174,19 @@
const void* data = "" protocolEncodedMessageKey, &dataSize);
Span<const uint8_t> encodedMessage { static_cast<const uint8_t*>(data), dataSize };
- decodeAndHandleMessage(messageType, encodedMessage, createReplySender(messageType, request));
+ decodeAndHandleMessage(xpc_dictionary_get_remote_connection(request), messageType, encodedMessage, createReplySender(messageType, request));
}
-void Daemon::connectionAdded(xpc_connection_t)
+void Daemon::connectionAdded(xpc_connection_t connection)
{
- // FIXME: Track connections
+ RELEASE_ASSERT(!m_connectionMap.contains(connection));
+ m_connectionMap.set(connection, WTF::makeUnique<ClientConnection>(connection));
}
-void Daemon::connectionRemoved(xpc_connection_t)
+void Daemon::connectionRemoved(xpc_connection_t connection)
{
- // FIXME: Track connections
+ RELEASE_ASSERT(m_connectionMap.contains(connection));
+ m_connectionMap.remove(connection);
}
CompletionHandler<void(EncodedMessage&&)> Daemon::createReplySender(MessageType messageType, OSObjectPtr<xpc_object_t>&& request)
@@ -169,33 +203,56 @@
};
}
-void Daemon::decodeAndHandleMessage(MessageType messageType, Span<const uint8_t> encodedMessage, CompletionHandler<void(EncodedMessage&&)>&& replySender)
+void Daemon::decodeAndHandleMessage(xpc_connection_t connection, MessageType messageType, Span<const uint8_t> encodedMessage, CompletionHandler<void(EncodedMessage&&)>&& replySender)
{
ASSERT(messageTypeSendsReply(messageType) == !!replySender);
+ auto* clientConnection = toClientConnection(connection);
+
switch (messageType) {
case MessageType::EchoTwice:
- handleWebPushDMessageWithReply<MessageInfo::echoTwice>(encodedMessage, WTFMove(replySender));
+ handleWebPushDMessageWithReply<MessageInfo::echoTwice>(clientConnection, encodedMessage, WTFMove(replySender));
break;
case MessageType::GetOriginsWithPushAndNotificationPermissions:
- handleWebPushDMessageWithReply<MessageInfo::getOriginsWithPushAndNotificationPermissions>(encodedMessage, WTFMove(replySender));
+ handleWebPushDMessageWithReply<MessageInfo::getOriginsWithPushAndNotificationPermissions>(clientConnection, encodedMessage, WTFMove(replySender));
break;
case MessageType::DeletePushAndNotificationRegistration:
- handleWebPushDMessageWithReply<MessageInfo::deletePushAndNotificationRegistration>(encodedMessage, WTFMove(replySender));
+ handleWebPushDMessageWithReply<MessageInfo::deletePushAndNotificationRegistration>(clientConnection, encodedMessage, WTFMove(replySender));
break;
case MessageType::RequestSystemNotificationPermission:
- handleWebPushDMessageWithReply<MessageInfo::requestSystemNotificationPermission>(encodedMessage, WTFMove(replySender));
+ handleWebPushDMessageWithReply<MessageInfo::requestSystemNotificationPermission>(clientConnection, encodedMessage, WTFMove(replySender));
break;
+ case MessageType::SetHostAppAuditToken:
+ handleWebPushDMessage<MessageInfo::setHostAppAuditToken>(clientConnection, encodedMessage);
+ break;
+ case MessageType::SetDebugModeIsEnabled:
+ handleWebPushDMessage<MessageInfo::setDebugModeIsEnabled>(clientConnection, encodedMessage);
+ break;
}
}
-void Daemon::echoTwice(const String& message, CompletionHandler<void(const String&)>&& replySender)
+void Daemon::echoTwice(ClientConnection*, const String& message, CompletionHandler<void(const String&)>&& replySender)
{
replySender(makeString(message, message));
}
-void Daemon::requestSystemNotificationPermission(const String& originString, CompletionHandler<void(bool)>&& replySender)
+bool Daemon::canRegisterForNotifications(ClientConnection& connection)
{
+ if (connection.hostAppCodeSigningIdentifier().isEmpty()) {
+ NSLog(@"ClientConnection cannot interact with notifications: Unknown host application code signing identifier");
+ return false;
+ }
+
+ return true;
+}
+
+void Daemon::requestSystemNotificationPermission(ClientConnection* connection, const String& originString, CompletionHandler<void(bool)>&& replySender)
+{
+ if (!canRegisterForNotifications(*connection)) {
+ replySender(false);
+ return;
+ }
+
// FIXME: This is for an API testing checkpoint
// Next step is actually perform a persistent permissions request on a per-platform basis
m_inMemoryOriginStringsWithPermissionForTesting.add(originString);
@@ -202,15 +259,25 @@
replySender(true);
}
-void Daemon::getOriginsWithPushAndNotificationPermissions(CompletionHandler<void(const Vector<String>&)>&& replySender)
+void Daemon::getOriginsWithPushAndNotificationPermissions(ClientConnection* connection, CompletionHandler<void(const Vector<String>&)>&& replySender)
{
+ if (!canRegisterForNotifications(*connection)) {
+ replySender({ });
+ return;
+ }
+
// FIXME: This is for an API testing checkpoint
// Next step is actually gather persistent permissions from the system on a per-platform basis
replySender(copyToVector(m_inMemoryOriginStringsWithPermissionForTesting));
}
-void Daemon::deletePushAndNotificationRegistration(const String& originString, CompletionHandler<void(const String&)>&& replySender)
+void Daemon::deletePushAndNotificationRegistration(ClientConnection* connection, const String& originString, CompletionHandler<void(const String&)>&& replySender)
{
+ if (!canRegisterForNotifications(*connection)) {
+ replySender("Could not delete push and notification registrations for connection: Unknown host application code signing identifier");
+ return;
+ }
+
// FIXME: This is for an API testing checkpoint
// Next step is actually delete any persistent permissions on a per-platform basis
if (m_inMemoryOriginStringsWithPermissionForTesting.remove(originString))
@@ -219,4 +286,21 @@
replySender(makeString("Origin ", originString, " not registered for push or notifications"));
}
+void Daemon::setHostAppAuditToken(ClientConnection* clientConnection, const Vector<uint8_t>& tokenData)
+{
+ clientConnection->setHostAppAuditTokenData(tokenData);
+}
+
+void Daemon::setDebugModeIsEnabled(ClientConnection* clientConnection, bool enabled)
+{
+ clientConnection->setDebugModeIsEnabled(enabled);
+}
+
+ClientConnection* Daemon::toClientConnection(xpc_connection_t connection)
+{
+ auto clientConnection = m_connectionMap.get(connection);
+ RELEASE_ASSERT(clientConnection);
+ return clientConnection;
+}
+
} // namespace WebPushD
Modified: trunk/Source/WebKit/webpushd/WebPushDaemonMain.mm (286074 => 286075)
--- trunk/Source/WebKit/webpushd/WebPushDaemonMain.mm 2021-11-19 21:35:00 UTC (rev 286074)
+++ trunk/Source/WebKit/webpushd/WebPushDaemonMain.mm 2021-11-19 21:43:17 UTC (rev 286075)
@@ -64,9 +64,7 @@
const char* machServiceName = argv[2];
@autoreleasepool {
- // FIXME: Add a sandbox.
- // FIXME: Add an entitlement check.
- WebKit::startListeningForMachServiceConnections(machServiceName, nullptr, WebPushD::connectionAdded, WebPushD::connectionRemoved, WebPushD::connectionEventHandler);
+ WebKit::startListeningForMachServiceConnections(machServiceName, "com.apple.private.webkit.webpush", WebPushD::connectionAdded, WebPushD::connectionRemoved, WebPushD::connectionEventHandler);
WTF::initializeMainThread();
}
CFRunLoopRun();
Modified: trunk/Tools/ChangeLog (286074 => 286075)
--- trunk/Tools/ChangeLog 2021-11-19 21:35:00 UTC (rev 286074)
+++ trunk/Tools/ChangeLog 2021-11-19 21:43:17 UTC (rev 286075)
@@ -1,3 +1,16 @@
+2021-11-19 Brady Eidson <beid...@apple.com>
+
+ More webpushd architecture work
+ https://bugs.webkit.org/show_bug.cgi?id=233295
+
+ Reviewed by Alex Christensen.
+
+ * TestWebKitAPI/Configurations/TestWebKitAPI-iOS.entitlements:
+ * TestWebKitAPI/Configurations/TestWebKitAPI-macOS-internal.entitlements:
+ * TestWebKitAPI/Configurations/TestWebKitAPI-macOS.entitlements:
+ * TestWebKitAPI/Tests/WebKitCocoa/WebPushDaemon.mm:
+ (TestWebKitAPI::TEST):
+
2021-11-18 Jonathan Bedard <jbed...@apple.com>
[resultsdbpy] Move AuthedBlueprint to webkitflaskpy
Modified: trunk/Tools/TestWebKitAPI/Configurations/TestWebKitAPI-iOS.entitlements (286074 => 286075)
--- trunk/Tools/TestWebKitAPI/Configurations/TestWebKitAPI-iOS.entitlements 2021-11-19 21:35:00 UTC (rev 286074)
+++ trunk/Tools/TestWebKitAPI/Configurations/TestWebKitAPI-iOS.entitlements 2021-11-19 21:43:17 UTC (rev 286075)
@@ -10,6 +10,8 @@
<true/>
<key>com.apple.Pasteboard.paste-unchecked</key>
<true/>
+ <key>com.apple.private.webkit.webpush</key>
+ <true/>
<key>com.apple.private.xpc.launchd.job-manager</key>
<string>TestWebKitAPI</string>
</dict>
Modified: trunk/Tools/TestWebKitAPI/Configurations/TestWebKitAPI-macOS-internal.entitlements (286074 => 286075)
--- trunk/Tools/TestWebKitAPI/Configurations/TestWebKitAPI-macOS-internal.entitlements 2021-11-19 21:35:00 UTC (rev 286074)
+++ trunk/Tools/TestWebKitAPI/Configurations/TestWebKitAPI-macOS-internal.entitlements 2021-11-19 21:43:17 UTC (rev 286075)
@@ -4,6 +4,8 @@
<dict>
<key>com.apple.private.xpc.launchd.job-manager</key>
<string>TestWebKitAPI</string>
+ <key>com.apple.private.webkit.webpush</key>
+ <true/>
<key>com.apple.hid.manager.user-access-device</key>
<true/>
<key>com.apple.private.hid.client.event-filter</key>
Modified: trunk/Tools/TestWebKitAPI/Configurations/TestWebKitAPI-macOS.entitlements (286074 => 286075)
--- trunk/Tools/TestWebKitAPI/Configurations/TestWebKitAPI-macOS.entitlements 2021-11-19 21:35:00 UTC (rev 286074)
+++ trunk/Tools/TestWebKitAPI/Configurations/TestWebKitAPI-macOS.entitlements 2021-11-19 21:43:17 UTC (rev 286075)
@@ -8,6 +8,8 @@
<array>
<string>com.apple.TestWebKitAPI</string>
</array>
+ <key>com.apple.private.webkit.webpush</key>
+ <true/>
<key>com.apple.security.temporary-exception.sbpl</key>
<array>
<string>(allow mach-issue-extension (require-all (extension-class "com.apple.webkit.extension.mach")))</string>
Modified: trunk/Tools/TestWebKitAPI/Tests/WebKitCocoa/WebPushDaemon.mm (286074 => 286075)
--- trunk/Tools/TestWebKitAPI/Tests/WebKitCocoa/WebPushDaemon.mm 2021-11-19 21:35:00 UTC (rev 286074)
+++ trunk/Tools/TestWebKitAPI/Tests/WebKitCocoa/WebPushDaemon.mm 2021-11-19 21:43:17 UTC (rev 286075)
@@ -31,6 +31,8 @@
#import <WebKit/WKPreferencesPrivate.h>
#import <WebKit/WKUIDelegatePrivate.h>
#import <WebKit/_WKExperimentalFeature.h>
+#import <mach/mach_init.h>
+#import <mach/task.h>
#if PLATFORM(MAC) || PLATFORM(IOS)
@@ -156,7 +158,7 @@
}
// FIXME: Re-enable this test for Monterey+ once webkit.org/232857 is resolved.
-#if __MAC_OS_X_VERSION_MIN_REQUIRED >= 120000
+#if __MAC_OS_X_VERSION_MIN_REQUIRED < 110000 || __MAC_OS_X_VERSION_MIN_REQUIRED >= 120000
TEST(WebPushD, DISABLED_BasicCommunication)
#else
TEST(WebPushD, BasicCommunication)
@@ -165,16 +167,67 @@
NSURL *tempDir = setUpTestWebPushD();
auto connection = adoptNS(xpc_connection_create_mach_service("org.webkit.webpushtestdaemon.service", dispatch_get_main_queue(), 0));
- xpc_connection_set_event_handler(connection.get(), ^(xpc_object_t) { });
+
+ __block bool done = false;
+ xpc_connection_set_event_handler(connection.get(), ^(xpc_object_t request) {
+ if (xpc_get_type(request) != XPC_TYPE_DICTIONARY)
+ return;
+ const char* debugMessage = xpc_dictionary_get_string(request, "debug message");
+ if (!debugMessage)
+ return;
+
+ bool stringMatches = !strcmp(debugMessage, "[webpushd - TestWebKitAPI] Turned Debug Mode on");
+ if (!stringMatches)
+ stringMatches = !strcmp(debugMessage, "[webpushd - com.apple.WebKit.TestWebKitAPI] Turned Debug Mode on");
+
+ EXPECT_TRUE(stringMatches);
+
+ done = true;
+ });
+
xpc_connection_activate(connection.get());
+
+ audit_token_t token = { 0, 0, 0, 0, 0, 0, 0, 0 };
+ mach_msg_type_number_t auditTokenCount = TASK_AUDIT_TOKEN_COUNT;
+ kern_return_t result = task_info(mach_task_self(), TASK_AUDIT_TOKEN, (task_info_t)(&token), &auditTokenCount);
+ if (result != KERN_SUCCESS) {
+ EXPECT_TRUE(false);
+ return;
+ }
+
+ // Send audit token
+ {
+ std::array<uint8_t, 40> encodedMessage;
+ encodedMessage.fill(0);
+ encodedMessage[0] = 32;
+ memcpy(&encodedMessage[8], &token, sizeof(token));
+ auto dictionary = adoptNS(xpc_dictionary_create(nullptr, nullptr, 0));
+ xpc_dictionary_set_uint64(dictionary.get(), "protocol version", 1);
+ xpc_dictionary_set_uint64(dictionary.get(), "message type", 5);
+ xpc_dictionary_set_data(dictionary.get(), "encoded message", encodedMessage.data(), encodedMessage.size());
+ xpc_connection_send_message(connection.get(), dictionary.get());
+ }
+
+ // Enable debug messages, and wait for the resulting debug message
+ {
+ auto dictionary = adoptNS(xpc_dictionary_create(nullptr, nullptr, 0));
+ std::array<uint8_t, 1> encodedMessage { 1 };
+ xpc_dictionary_set_uint64(dictionary.get(), "protocol version", 1);
+ xpc_dictionary_set_uint64(dictionary.get(), "message type", 6);
+ xpc_dictionary_set_data(dictionary.get(), "encoded message", encodedMessage.data(), encodedMessage.size());
+
+ xpc_connection_send_message(connection.get(), dictionary.get());
+ TestWebKitAPI::Util::run(&done);
+ }
+
+ // Echo and wait for a reply
auto dictionary = adoptNS(xpc_dictionary_create(nullptr, nullptr, 0));
-
std::array<uint8_t, 10> encodedString { 5, 0, 0, 0, 1, 'h', 'e', 'l', 'l', 'o' };
xpc_dictionary_set_uint64(dictionary.get(), "protocol version", 1);
xpc_dictionary_set_uint64(dictionary.get(), "message type", 1);
xpc_dictionary_set_data(dictionary.get(), "encoded message", encodedString.data(), encodedString.size());
-
- __block bool done = false;
+
+ done = false;
xpc_connection_send_message_with_reply(connection.get(), dictionary.get(), dispatch_get_main_queue(), ^(xpc_object_t reply) {
if (xpc_get_type(reply) != XPC_TYPE_DICTIONARY) {
NSLog(@"Unexpected non-dictionary: %@", reply);
@@ -202,7 +255,7 @@
)WEBPUSHRESOURCE";
// FIXME: Re-enable this test for Monterey+ once webkit.org/232857 is resolved.
-#if __MAC_OS_X_VERSION_MIN_REQUIRED >= 120000
+#if __MAC_OS_X_VERSION_MIN_REQUIRED < 110000 || __MAC_OS_X_VERSION_MIN_REQUIRED >= 120000
TEST(WebPushD, DISABLED_PermissionManagement)
#else
TEST(WebPushD, PermissionManagement)