Skip to content

Commit

Permalink
Provide canSuspend info to didExceedMemoryFootprintThreshold event
Browse files Browse the repository at this point in the history
https://bugs.webkit.org/show_bug.cgi?id=270646
rdar://124165615

Reviewed by Chris Dumez.

We fire the didExceedMemoryFootprintThreshold analytics event to detect sites and/or processes with
excessive memory usage. We also want to log whether or not those sites are ever allowed to suspend
in the event.

I also changed the event to log the threshold being violated rather than the actual footprint value
of the process. This works better with the way we want to analyze the data.

* Source/WTF/wtf/MemoryPressureHandler.cpp:
(WTF::MemoryPressureHandler::measurementTimerFired):
* Source/WebKit/UIProcess/API/Cocoa/WKWebsiteDataStore.mm:
* Source/WebKit/UIProcess/API/Cocoa/_WKWebsiteDataStoreDelegate.h:
* Source/WebKit/UIProcess/WebPageProxy.cpp:
(WebKit::WebPageProxy::hasAllowedToRunInTheBackgroundActivity const):
* Source/WebKit/UIProcess/WebPageProxy.h:
* Source/WebKit/UIProcess/WebProcessProxy.cpp:
(WebKit::WebProcessProxy::didExceedMemoryFootprintThreshold):
* Source/WebKit/UIProcess/WebsiteData/WebsiteDataStoreClient.h:
(WebKit::WebsiteDataStoreClient::didExceedMemoryFootprintThreshold):
* Tools/TestWebKitAPI/Tests/WebKitCocoa/MemoryFootprintThreshold.mm:
(-[MemoryFootprintDelegate websiteDataStore:domain:didExceedMemoryFootprintThreshold:withPageCount:processLifetime:inForeground:wasPrivateRelayed:canSuspend:]):
(-[MemoryFootprintDelegate websiteDataStore:domain:didExceedMemoryFootprintThreshold:withPageCount:processLifetime:inForeground:wasPrivateRelayed:]): Deleted.

Canonical link: https://commits.webkit.org/276032@main
  • Loading branch information
bnham committed Mar 13, 2024
1 parent 67969c2 commit 81b1ab5
Show file tree
Hide file tree
Showing 8 changed files with 21 additions and 12 deletions.
4 changes: 2 additions & 2 deletions Source/WTF/wtf/MemoryPressureHandler.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -235,8 +235,8 @@ void MemoryPressureHandler::measurementTimerFired()
#endif

while (m_memoryFootprintNotificationThresholds.size() && footprint > m_memoryFootprintNotificationThresholds.last()) {
m_memoryFootprintNotificationThresholds.removeLast();
m_memoryFootprintNotificationHandler(footprint);
auto notificationThreshold = m_memoryFootprintNotificationThresholds.takeLast();
m_memoryFootprintNotificationHandler(notificationThreshold);
}

auto killThreshold = thresholdForMemoryKill();
Expand Down
6 changes: 3 additions & 3 deletions Source/WebKit/UIProcess/API/Cocoa/WKWebsiteDataStore.mm
Original file line number Diff line number Diff line change
Expand Up @@ -82,7 +82,7 @@
, m_hasNotifyBackgroundFetchChangeSelector([m_delegate.get() respondsToSelector:@selector(notifyBackgroundFetchChange:change:)])
, m_hasWindowProxyPropertyAccessSelector([m_delegate.get() respondsToSelector:@selector(websiteDataStore:domain:didOpenDomainViaWindowOpen:withProperty:directly:)])
, m_hasDidAllowPrivateTokenUsageByThirdPartyForTestingSelector([m_delegate.get() respondsToSelector:@selector(websiteDataStore:didAllowPrivateTokenUsageByThirdPartyForTesting:forResourceURL:)])
, m_hasDidExceedMemoryFootprintThresholdSelector([m_delegate.get() respondsToSelector:@selector(websiteDataStore:domain:didExceedMemoryFootprintThreshold:withPageCount:processLifetime:inForeground:wasPrivateRelayed:)])
, m_hasDidExceedMemoryFootprintThresholdSelector([m_delegate.get() respondsToSelector:@selector(websiteDataStore:domain:didExceedMemoryFootprintThreshold:withPageCount:processLifetime:inForeground:wasPrivateRelayed:canSuspend:)])
{
}

Expand Down Expand Up @@ -302,12 +302,12 @@ void didAllowPrivateTokenUsageByThirdPartyForTesting(bool wasAllowed, WTF::URL&&
[m_delegate.getAutoreleased() websiteDataStore:m_dataStore.getAutoreleased() didAllowPrivateTokenUsageByThirdPartyForTesting:wasAllowed forResourceURL:resourceURL];
}

void didExceedMemoryFootprintThreshold(size_t footprint, const String& domain, unsigned pageCount, Seconds processLifetime, bool inForeground, WebCore::WasPrivateRelayed wasPrivateRelayed)
void didExceedMemoryFootprintThreshold(size_t footprint, const String& domain, unsigned pageCount, Seconds processLifetime, bool inForeground, WebCore::WasPrivateRelayed wasPrivateRelayed, CanSuspend canSuspend)
{
if (!m_hasDidExceedMemoryFootprintThresholdSelector)
return;

[m_delegate.getAutoreleased() websiteDataStore:m_dataStore.getAutoreleased() domain:(NSString *)domain didExceedMemoryFootprintThreshold:footprint withPageCount:pageCount processLifetime:processLifetime.seconds() inForeground:inForeground wasPrivateRelayed:wasPrivateRelayed == WebCore::WasPrivateRelayed::Yes];
[m_delegate.getAutoreleased() websiteDataStore:m_dataStore.getAutoreleased() domain:(NSString *)domain didExceedMemoryFootprintThreshold:footprint withPageCount:pageCount processLifetime:processLifetime.seconds() inForeground:inForeground wasPrivateRelayed:wasPrivateRelayed == WebCore::WasPrivateRelayed::Yes canSuspend:canSuspend == CanSuspend::Yes];
}

WeakObjCPtr<WKWebsiteDataStore> m_dataStore;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -71,5 +71,5 @@ WK_API_AVAILABLE(macos(10.15), ios(13.0))
- (void)notifyBackgroundFetchChange:(NSString *)backgroundFetchIdentifier change:(WKBackgroundFetchChange)change;
- (void)websiteDataStore:(WKWebsiteDataStore *)dataStore domain:(NSString *)registrableDomain didOpenDomainViaWindowOpen:(NSString *)openedRegistrableDomain withProperty:(WKWindowProxyProperty)property directly:(BOOL)directly;
- (void)websiteDataStore:(WKWebsiteDataStore *)dataStore didAllowPrivateTokenUsageByThirdPartyForTesting:(BOOL)wasAllowed forResourceURL:(NSURL *)resourceURL;
- (void)websiteDataStore:(WKWebsiteDataStore *)dataStore domain:(NSString *)registrableDomain didExceedMemoryFootprintThreshold:(size_t)footprint withPageCount:(NSUInteger)pageCount processLifetime:(NSTimeInterval)processLifetime inForeground:(BOOL)inForeground wasPrivateRelayed:(BOOL)wasPrivateRelayed;
- (void)websiteDataStore:(WKWebsiteDataStore *)dataStore domain:(NSString *)registrableDomain didExceedMemoryFootprintThreshold:(size_t)footprint withPageCount:(NSUInteger)pageCount processLifetime:(NSTimeInterval)processLifetime inForeground:(BOOL)inForeground wasPrivateRelayed:(BOOL)wasPrivateRelayed canSuspend:(BOOL)canSuspend;
@end
5 changes: 5 additions & 0 deletions Source/WebKit/UIProcess/WebPageProxy.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -6643,6 +6643,11 @@ void WebPageProxy::processIsNoLongerAssociatedWithPage(WebProcessProxy& process)
m_navigationState->clearNavigationsFromProcess(process.coreProcessIdentifier());
}

bool WebPageProxy::hasAllowedToRunInTheBackgroundActivity() const
{
return internals().pageAllowedToRunInTheBackgroundActivityDueToTitleChanges || internals().pageAllowedToRunInTheBackgroundActivityDueToNotifications;
}

void WebPageProxy::didReceiveTitleForFrame(FrameIdentifier frameID, const String& title, const UserData& userData)
{
Ref protectedPageClient { pageClient() };
Expand Down
1 change: 1 addition & 0 deletions Source/WebKit/UIProcess/WebPageProxy.h
Original file line number Diff line number Diff line change
Expand Up @@ -2401,6 +2401,7 @@ class WebPageProxy final : public API::ObjectImpl<API::Object::Type::Page>, publ
#endif

bool hasValidAudibleActivity() const;
bool hasAllowedToRunInTheBackgroundActivity() const;

private:
WebPageProxy(PageClient&, WebProcessProxy&, Ref<API::PageConfiguration>&&);
Expand Down
4 changes: 3 additions & 1 deletion Source/WebKit/UIProcess/WebProcessProxy.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -2005,6 +2005,7 @@ void WebProcessProxy::didExceedMemoryFootprintThreshold(size_t footprint)

String domain;
bool wasPrivateRelayed = false;
bool hasAllowedToRunInTheBackgroundActivity = false;

for (auto& page : this->pages()) {
#if ENABLE(PUBLIC_SUFFIX_LIST)
Expand All @@ -2015,14 +2016,15 @@ void WebProcessProxy::didExceedMemoryFootprintThreshold(size_t footprint)
domain = "multiple"_s;

wasPrivateRelayed = wasPrivateRelayed || page->pageLoadState().wasPrivateRelayed();
hasAllowedToRunInTheBackgroundActivity = hasAllowedToRunInTheBackgroundActivity || page->hasAllowedToRunInTheBackgroundActivity();
#endif
}

if (domain.isEmpty())
domain = "unknown"_s;

auto activeTime = totalForegroundTime() + totalBackgroundTime() + totalSuspendedTime();
dataStore->client().didExceedMemoryFootprintThreshold(footprint, domain, pageCount(), activeTime, throttler().currentState() == ProcessThrottleState::Foreground, wasPrivateRelayed ? WebCore::WasPrivateRelayed::Yes : WebCore::WasPrivateRelayed::No);
dataStore->client().didExceedMemoryFootprintThreshold(footprint, domain, pageCount(), activeTime, throttler().currentState() == ProcessThrottleState::Foreground, wasPrivateRelayed ? WebCore::WasPrivateRelayed::Yes : WebCore::WasPrivateRelayed::No, hasAllowedToRunInTheBackgroundActivity ? WebsiteDataStoreClient::CanSuspend::No : WebsiteDataStoreClient::CanSuspend::Yes);
}

void WebProcessProxy::didExceedCPULimit()
Expand Down
3 changes: 2 additions & 1 deletion Source/WebKit/UIProcess/WebsiteData/WebsiteDataStoreClient.h
Original file line number Diff line number Diff line change
Expand Up @@ -118,7 +118,8 @@ class WebsiteDataStoreClient {
{
}

virtual void didExceedMemoryFootprintThreshold(size_t, const String&, unsigned, Seconds, bool inForeground, WebCore::WasPrivateRelayed)
enum class CanSuspend : bool { No, Yes };
virtual void didExceedMemoryFootprintThreshold(size_t, const String&, unsigned, Seconds, bool inForeground, WebCore::WasPrivateRelayed, CanSuspend)
{
}
};
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -63,7 +63,7 @@ @interface MemoryFootprintDelegate : NSObject<_WKWebsiteDataStoreDelegate> {

@implementation MemoryFootprintDelegate

- (void)websiteDataStore:(WKWebsiteDataStore *)dataStore domain:(NSString *)registrableDomain didExceedMemoryFootprintThreshold:(size_t)footprint withPageCount:(NSUInteger)pageCount processLifetime:(NSTimeInterval)processLifetime inForeground:(BOOL)inForeground wasPrivateRelayed:(BOOL)wasPrivateRelayed
- (void)websiteDataStore:(WKWebsiteDataStore *)dataStore domain:(NSString *)registrableDomain didExceedMemoryFootprintThreshold:(size_t)footprint withPageCount:(NSUInteger)pageCount processLifetime:(NSTimeInterval)processLifetime inForeground:(BOOL)inForeground wasPrivateRelayed:(BOOL)wasPrivateRelayed canSuspend:(BOOL)canSuspend
{
_footprints.append(footprint);

Expand Down Expand Up @@ -95,9 +95,9 @@ - (void)websiteDataStore:(WKWebsiteDataStore *)dataStore domain:(NSString *)regi
TestWebKitAPI::Util::run(&delegate->_done);

EXPECT_EQ(delegate->_footprints.size(), 3u);
EXPECT_GT(delegate->_footprints[0], 25u << 20);
EXPECT_GT(delegate->_footprints[1], 50u << 20);
EXPECT_GT(delegate->_footprints[2], 100u << 20);
EXPECT_EQ(delegate->_footprints[0], 25u << 20);
EXPECT_EQ(delegate->_footprints[1], 50u << 20);
EXPECT_EQ(delegate->_footprints[2], 100u << 20);
}

#endif // ENABLE(PERIODIC_MEMORY_MONITOR)

0 comments on commit 81b1ab5

Please sign in to comment.