Skip to content
This repository was archived by the owner on Feb 25, 2025. It is now read-only.

Optimize UI & GPU thread QoS for iOS #15673

Closed
wants to merge 1 commit into from
Closed
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
25 changes: 21 additions & 4 deletions shell/platform/darwin/ios/framework/Source/FlutterEngine.mm
Original file line number Diff line number Diff line change
Expand Up @@ -409,10 +409,6 @@ - (BOOL)createShell:(NSString*)entrypoint libraryURI:(NSString*)libraryURI {
// initialized.
fml::MessageLoop::EnsureInitializedForCurrentThread();

_threadHost = {threadLabel.UTF8String, // label
flutter::ThreadHost::Type::UI | flutter::ThreadHost::Type::GPU |
flutter::ThreadHost::Type::IO};

// Lambda captures by pointers to ObjC objects are fine here because the
// create call is
// synchronous.
Expand All @@ -435,12 +431,18 @@ - (BOOL)createShell:(NSString*)entrypoint libraryURI:(NSString*)libraryURI {
// TODO(amirh/chinmaygarde): remove this, and dynamically change the thread configuration.
// https://github.com/flutter/flutter/issues/23975

_threadHost = {threadLabel.UTF8String, // label
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That the GPU thread will no longer be created when there are platform views in the scene is an artifact of a previous implementation. This has been fixed #16068 and will cause issues with that line of work.

flutter::ThreadHost::Type::UI | flutter::ThreadHost::Type::IO};

flutter::TaskRunners task_runners(threadLabel.UTF8String, // label
fml::MessageLoop::GetCurrent().GetTaskRunner(), // platform
fml::MessageLoop::GetCurrent().GetTaskRunner(), // gpu
_threadHost.ui_thread->GetTaskRunner(), // ui
_threadHost.io_thread->GetTaskRunner() // io
);

[self setupQualityOfService:task_runners];

// Create the shell. This is a blocking operation.
_shell = flutter::Shell::Create(std::move(task_runners), // task runners
std::move(windowData), // window data
Expand All @@ -449,12 +451,19 @@ - (BOOL)createShell:(NSString*)entrypoint libraryURI:(NSString*)libraryURI {
on_create_rasterizer // rasterzier creation
);
} else {
_threadHost = {threadLabel.UTF8String, // label
flutter::ThreadHost::Type::UI | flutter::ThreadHost::Type::GPU |
flutter::ThreadHost::Type::IO};

flutter::TaskRunners task_runners(threadLabel.UTF8String, // label
fml::MessageLoop::GetCurrent().GetTaskRunner(), // platform
_threadHost.gpu_thread->GetTaskRunner(), // gpu
_threadHost.ui_thread->GetTaskRunner(), // ui
_threadHost.io_thread->GetTaskRunner() // io
);

[self setupQualityOfService:task_runners];

// Create the shell. This is a blocking operation.
_shell = flutter::Shell::Create(std::move(task_runners), // task runners
std::move(windowData), // window data
Expand Down Expand Up @@ -682,6 +691,14 @@ - (void)setIsGpuDisabled:(BOOL)value {
_isGpuDisabled = value;
}

- (void)setupQualityOfService:(flutter::TaskRunners&)task_runners {
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This needs to be done for all threads managed by the engine. This includes the IO thread as well as the worker task runners (QOS_CLASS_BACKGROUND). I suggest exposing this via the platform view creation callback. That way, all platforms are given the opportunity to set thread priorities on all threads managed by the engine.

task_runners.GetUITaskRunner()->PostTask(
[] { pthread_set_qos_class_self_np(QOS_CLASS_USER_INTERACTIVE, 0); });

task_runners.GetGPUTaskRunner()->PostTask(
[] { pthread_set_qos_class_self_np(QOS_CLASS_USER_INTERACTIVE, 0); });
}

@end

@implementation FlutterEngineRegistrar {
Expand Down