SurfaceFlinger 启动流程
基础流程
init.rc-> surfaceflinger.rc-->main_surfaceflinger.cpp-->SurfaceFlinger.cpp-->init();
基础类和rc
Init.rc
路径
system/core/rootdir/init.rc
原理
Init.rc 文件在加载的时候会加载所有的core服务
surfaceflinger.rc 属于 class core animation
class_start core //启动所有属于core的核心rc
surfaceflinger.rc
路径
frameworks/native/services/surfaceflinger/surfaceflinger.rc
service surfaceflinger /system/bin/surfaceflinger
class core animation
user system
group graphics drmrpc readproc
capabilities SYS_NICE
onrestart restart zygote
task_profiles HighPerformance
socket pdx/system/vr/display/client stream 0666 system graphics u:object_r:pdx_display_client_endpoint_socket:s0
socket pdx/system/vr/display/manager stream 0666 system graphics u:object_r:pdx_display_manager_endpoint_socket:s0
socket pdx/system/vr/display/vsync stream 0666 system graphics u:object_r:pdx_display_vsync_endpoint_socket:s0
Surfaceflinger.rc中可以看到class core,所以Init.rc 中 class_start core ,就会执行surfaceflinger.rc这个文件。之后会执行Main_surfaceflinger.cpp
资料
surfaceFlinger相关路径
frameworks/native/services/surfaceflinger
main_surfaceflinger.cpp
总结
- 创建SurfaceFlinger 对象 ,调用了SurfaceFlinger::onFrisrRef()
- 调用sf的init()进行初始化
- 注册到ServiceManger
- 调用sf的run()方法
int main(int,char**){
signal(SIGPIPE,SIG_IGN); //表示让系统忽略SIGPIPE信号,SIGPIPE信号的默认处理是终止程序
//sf service启动时要设置binder的线程池,用于设置 当前进程用于hwbinder通信的最大线程数:
hardware::configureRpcThreadpool(1 /* maxThreads */,false /* callerWillJoin */);
//启动图形分配器服务
startGraphicsAllocatorService();
//sf进程启动后,限制其进程中binder线程数量为4
ProcessState::self()->setThreadPoolMaxThreadCount(4);
//start the thread pool
sp<ProcessState> ps(ProcessState::self());
ps->startThreadPool();//开启线程池
// 调用 SurfaceFlingerFactory.cpp 中的创建方法 surfaceFlinger 继承RefBase 一旦new出对象赋值给sp指针,立马触发 SurfaceFlinger.onFirstRef方法
// // Implements RefBase surfaceFlinger.h中
// void onFirstRef() override;
sp<SurfaceFlinger> flinger = surfaceFlinger::createSurfaceFligner();
setpriority(PRIO_PROCESS,0,PRIORITY_URGENT_DISPLAY);//PRIO_PRCESS设置进程优先级,0是当前进程,PRIORITY_URGENT_DISPLAY是优先级档位,
set_sched_policy(0,SP_FOREGROUND);//设置调度策略,优先级
if(cpusets_enable()) set_cpuset_policy(0,SP_SYSTEM);//cpu 策略,sf被限制在了小核
//调用init()方法
flinger->init();
//publish surface flinger
sp<IServiceManager> sm(defaultServiceManager());
//添加surfaceflinger服务到 ServiceMananger
sm>addService(String16(SurfaceFlinger::getServiceName()),flinger,false,IServiceManger::DUMP_FLAG_PRIORITY_CRITICAL | IServiceManager::DUMP_FLAG_PROTO);
//依赖于SF在上面注册,启动DisplayService
startDisplayService();
if(SurfaceFlinger::setSchedFifo(true) != NO_ERROR){
ALOGW("Couldn't set to SCHED_FIFO: %s",strerror(errno));
//run surface flinger in this thread
flinger->run();
return 0;
}
SurfaceFlinger.h
class SurfaceFlinger : public BnSurfaceComposer,//实现了ISurfaceComposer接口的bn服务端
public PriorityDumper,//dump信息 priotityDumper
private IBinder::DeathRecipient,
private HWC2::ComposerCallback,//监听Composer Hal的一些事件,比如 Vsync
private ISchedulerCallback//
{//
SurfaceFlingerFactory.h
定义了各种creat方法, 用factory 创建实现了对应方法,默认使用DefaultFactory->SurfaceFlingerDefaultFactory.cpp
SurfaceFlingerFactory.cpp
#include "SurfaceFlinger.h"
#include "SurfaceFlingerDefaultFactory.h"
namespace android::surfaceflinger {
sp<SurfaceFlinger> createSurfaceFlinger() {
static DefaultFactory factory;//传入了一个factory
return new SurfaceFlinger(factory);
}
}
SurfaceFlinger.cpp
run()
//native消息开始转动
void SurfaceFlinger::run() {
while (true) {
mEventQueue->waitMessage();
}
}
init()
梳理:
- 初始化RenderEngine对象用于client 合成模式(gpu)合成
- 初始化hwComposer 注册回调mCompositionEngine->getHwComposer().setCallBack(this),hal会回调一些方法
- 处理Display显示屏幕的热插拔和更改的事件 processDisplayHotplugEventsLocked();
- 初始化显示设备 initializeDisplays();
- 开启一个设置属性的线程,在这个线程用property_set 设置一些属性值 mStartPropertySetThread->Start()
//初始化
void SurfaceFlinger::init() {
ALOGI( "SurfaceFlinger's main thread ready to run. "
"Initializing graphics H/W...");
Mutex::Autolock _l(mStateLock);
//初始化引擎
mCompositionEngine->setRenderEngine(renderengine::RenderEngine::create(
renderengine::RenderEngineCreationArgs::Builder()
.setPixelFormat(static_cast<int32_t>(defaultCompositionPixelFormat))
.setImageCacheSize(maxFrameBufferAcquiredBuffers)
.setUseColorManagerment(useColorManagement)
.setEnableProtectedContext(enable_protected_contents(false))
.setPrecacheToneMapperShaderOnly(false)
.setSupportsBackgroundBlur(mSupportsBlur)
.setContextPriority(
useContextPriority
? renderengine::RenderEngine::ContextPriority::REALTIME
: renderengine::RenderEngine::ContextPriority::MEDIUM)
.build()));
// Set SF main policy after initializing RenderEngine which has its own policy.
if (!SetTaskProfiles(0, {"SFMainPolicy"})) {
ALOGW("Failed to set main task profile");
}
mCompositionEngine->setTimeStats(mTimeStats);
mCompositionEngine->setHwComposer(getFactory().createHWComposer(mHwcServiceName));
mCompositionEngine->getHwComposer().setCallback(this);
ClientCache::getInstance().setRenderEngine(&getRenderEngine());
if (base::GetBoolProperty("debug.sf.enable_hwc_vds"s, false)) {
enableHalVirtualDisplays(true);
}
// 热插拔处理
processDisplayHotplugEventsLocked();
const auto display = getDefaultDisplayDeviceLocked();
LOG_ALWAYS_FATAL_IF(!display, "Missing internal display after registering composer callback.");
const auto displayId = display->getPhysicalId();
LOG_ALWAYS_FATAL_IF(!getHwComposer().isConnected(displayId),
"Internal display is disconnected.");
// initialize our drawing state
mDrawingState = mCurrentState;
// 初始化display信息
initializeDisplays();
mPowerAdvisor.init();
char primeShaderCache[PROPERTY_VALUE_MAX];
property_get("service.sf.prime_shader_cache", primeShaderCache, "1");
if (atoi(primeShaderCache)) {
if (setSchedFifo(false) != NO_ERROR) {
ALOGW("Can't set SCHED_OTHER for primeCache");
}
mRenderEnginePrimeCacheFuture = getRenderEngine().primeCache();
if (setSchedFifo(true) != NO_ERROR) {
ALOGW("Can't set SCHED_OTHER for primeCache");
}
}
getRenderEngine().onPrimaryDisplaySizeChanged(display->getSize());
// Inform native graphics APIs whether the present timestamp is supported:
const bool presentFenceReliable =
!getHwComposer().hasCapability(hal::Capability::PRESENT_FENCE_IS_NOT_RELIABLE);
mStartPropertySetThread = getFactory().createStartPropertySetThread(presentFenceReliable);
//开启一个设置属性的线程,在这个线程中使用property_set设置一些属性
if (mStartPropertySetThread->Start() != NO_ERROR) {
ALOGE("Run StartPropertySetThread failed!");
}
ALOGV("Done initializing");
}
onFirstRef()
//初始化eventQueue
void SurfaceFlinger::onFirstRef() {
mEventQueue->init(this);
}
HWC2.h
SurfaceFlinger实现了该接口,该接口处理了VSYNC信号,热拔插显示器等
实现这个接口可以接收来自HWC的事件, 这些callBack都是 hwc Hal 通过hwcBinder 跨进程传递过来的。
第一次注册callBack的时候,onComposerHalHotplug 会立即在注册callBack的线程中调用。并跨进程回调
SurfaceFlinger::onComposerHalHotplug(),也就说SurfaceFlinger调用 init() 注册回调以后,立马会收到onComposerHalHotplug的回调。
struct ComposerCallback {
//热拔插
virtual void onComposerHalHotplug(hal::HWDisplayId, hal::Connection) = 0;
virtual void onComposerHalRefresh(hal::HWDisplayId) = 0;
//Vsync
virtual void onComposerHalVsync(hal::HWDisplayId, int64_t timestamp,
std::optional<hal::VsyncPeriodNanos>) = 0;
virtual void onComposerHalVsyncPeriodTimingChanged(hal::HWDisplayId,
const hal::VsyncPeriodChangeTimeline&) = 0;
virtual void onComposerHalSeamlessPossible(hal::HWDisplayId) = 0;
protected:
~ComposerCallback() = default;
};
Native消息机制
相关类
SurfaceFlinger.h
//变量声明
std::unique_ptr<MessageQueue> mEventQueue;
SurfaceFlinger.cpp
SurfaceFlinger::SurfaceFlinger(Factory& factory, SkipInitializationTag)
: mFactory(factory),
mInterceptor(mFactory.createSurfaceInterceptor()),
mTimeStats(std::make_shared<impl::TimeStats>()),
mFrameTracer(mFactory.createFrameTracer()),
mFrameTimeline(mFactory.createFrameTimeline(mTimeStats, getpid())),
//sf 在构造函数声明了消息队列 但是是通过factory 完成的 //SurfaceFlingerDefaultFactory.createMessageQueue
mEventQueue(mFactory.createMessageQueue()),
mCompositionEngine(mFactory.createCompositionEngine()),
mHwcServiceName(base::GetProperty("debug.sf.hwc_service_name"s, "default"s)),
mTunnelModeEnabledReporter(new TunnelModeEnabledReporter()),
mInternalDisplayDensity(getDensityFromProperty("ro.sf.lcd_density", true)),
mEmulatedDisplayDensity(getDensityFromProperty("qemu.sf.lcd_density", false)),
mPowerAdvisor(*this) {
ALOGI("Using HWComposer service: %s", mHwcServiceName.c_str());
mSetInputWindowsListener = new SetInputWindowsListener([&]() { setInputWindowsFinished(); });
}
SurfaceFlingerDefaultFactory.cpp
std::unique_ptr<MessageQueue> DefaultFactory::createMessageQueue() {
return std::make_unique<android::impl::MessageQueue>();
}
涉及类
MessageQueue && Looper && Handler
路径
/frameworks/native/services/surfaceflinger/Scheduler/MessageQueue.cpp
/frameworks/native/services/surfaceflinger/Scheduler/MessageQueue.h
/system/core/include/utils/Looper.h -->Message 在Looper.h里是个结构体
/system/core/libutils/Looper.cpp
//资料: 原理 https://www.cnblogs.com/roger-yu/p/15099541.html
// 应用 https://www.cnblogs.com/roger-yu/p/15100416.html
分析
- MessageQueue :维护消息队列,提供发送消息方法等
- Handler: 实现handleMessage 处理消息 内部实现类
- Looper
MessageQueue.h
class MessageQueue {
public:
enum {
INVALIDATE = 0,
REFRESH = 1,
};
virtual ~MessageQueue() = default;
virtual void init(const sp<SurfaceFlinger>& flinger) = 0;
virtual void initVsync(scheduler::VSyncDispatch&, frametimeline::TokenManager&,
std::chrono::nanoseconds workDuration) = 0;
virtual void setDuration(std::chrono::nanoseconds workDuration) = 0;
virtual void setInjector(sp<EventThreadConnection>) = 0;
virtual void waitMessage() = 0;
virtual void postMessage(sp<MessageHandler>&&) = 0;
virtual void invalidate() = 0;
virtual void refresh() = 0;
virtual std::optional<std::chrono::steady_clock::time_point> nextExpectedInvalidate() = 0;
};
MessageQueue.cpp
// SurfaceFlinger中的 onFirstRef 就调用该方法 mEventQueue->init(this);
void MessageQueue::init(const sp<SurfaceFlinger>& flinger) {
mFlinger = flinger;//sf自己
mLooper = new Looper(true);//消息队列和等待监测的fd队列,用户调用pullonec或者pollAll时候 会进行判断
mHandler = new Handler(*this);//消息对象通过handlerMessage 处理对应逻辑
}
//发送消息
void MessageQueue::postMessage(sp<MessageHandler>&& handler) {
mLooper->sendMessage(handler, Message());
}
//检查是否有消息 需要处理 如果有调用messageHandler去处理
void MessageQueue::waitMessage() {
do {
IPCThreadState::self()->flushCommands();
int32_t ret = mLooper->pollOnce(-1);
switch (ret) {
case Looper::POLL_WAKE:
case Looper::POLL_CALLBACK:
continue;
case Looper::POLL_ERROR:
ALOGE("Looper::POLL_ERROR");
continue;
case Looper::POLL_TIMEOUT:
// timeout (should not happen)
continue;
default:
// should not happen
ALOGE("Looper::pollOnce() returned unknown status %d", ret);
continue;
}
} while (true);
}
//sf 只关心INVALIDATE 和 REFRESH
void MessageQueue::Handler::handleMessage(const Message& message) {
switch (message.what) {
case INVALIDATE:
mEventMask.fetch_and(~eventMaskInvalidate);
mQueue.mFlinger->onMessageReceived(message.what, mVsyncId, mExpectedVSyncTime);
break;
case REFRESH:
mEventMask.fetch_and(~eventMaskRefresh);
mQueue.mFlinger->onMessageReceived(message.what, mVsyncId, mExpectedVSyncTime);
break;
}
}
SurfaceFlinger (SF)个人梳理
SurfaceFlinger主要处理2个事件,Refresh和Invaildate。
基础流程
//消息轮训的启动
main_surfaceflinger.cpp
-->main()//创建SF,因为SF继承RefBase ,所以调用的SF中的onFirstRef
-->onFirstRef()
-->mEventQueue->init(this);
-->MessageQueue.init()//初始化handler,mflinger,Handler
--> flinger->run();
-->EventQueue->waitMessage()//这里 死循环等待mEventQueue->waitMessage();
//到此为止 sf 消息就跑起来了 而且一直等待消息
------------------------------------------------------------------------------------
//发送消息 调用looper sendMessage
MessageQueue.postMessage();
-->mLooper.sendMessage(handler, Message());
-->Looper.sendMessageAtTime()
-->//加入消息队列
--------------------------------------------------------------------------------------
//消息等待
MessageQueue.waitMessage()
-->mLooper->pollOnce(-1);
-->pollInner(timeoutMillis);
--> //符合条件调用下面代码handleMessage()
sp<MessageHandler> handler = messageEnvelope.handler;
Message message = messageEnvelope.message;
mMessageEnvelopes.removeAt(0);
mSendingMessage = true;
mLock.unlock();
handler->handleMessage(message);
-->MessageQueue.h 中 Handler.handleMessage()
-->MessageQueue.cpp //回调flinger中的onMessageReceived 因为传过来的是this
void MessageQueue::Handler::handleMessage(const Message& message) {
switch (message.what) {
case INVALIDATE:
mEventMask.fetch_and(~eventMaskInvalidate);
mQueue.mFlinger->onMessageReceived(message.what, mVsyncId, mExpectedVSyncTime);
break;
case REFRESH:
mEventMask.fetch_and(~eventMaskRefresh);
mQueue.mFlinger->onMessageReceived(message.what, mVsyncId, mExpectedVSyncTime);
break;
}
}
-->SurfaceFlinger.cpp //进行对应处理
void SurfaceFlinger::onMessageReceived(int32_t what, int64_t vsyncId, nsecs_t expectedVSyncTime) {
switch (what) {
case MessageQueue::INVALIDATE: {
onMessageInvalidate(vsyncId, expectedVSyncTime);-->最后也会调用onMessageRefresh()
break;
}
case MessageQueue::REFRESH: {
onMessageRefresh();
break;
}
}
}
-----------------------------------------------------------------------------------------
//主线程的回调 等待vsync回调主线程 这块没研究
SurfaceFlinger::onMessageRefresh()--> signalLayerUpdate()--> mEventQueue->invalidate();
--> mVsync.expectedWakeupTime =
mVsync.registration->schedule({.workDuration = mVsync.workDuration.get().count(),
.readyDuration = 0,
.earliestVsync = mVsync.lastCallbackTime.count()});
问题和汇总
SurfaceFlinger职责
-
接收缓冲区,对图形数据进行合成,然后发送屏幕渲染。
-
SF并非真的渲染对象,而是将应用传递进来的图元数据进行加工,教给cpu和gpu绘制。所有的应用都会将渲染逻辑教给SF。
-
每个应用都有一个Surface 作为一个图元传递单元,SF向这个服务端传递图元数据,
-
SF和AMS ,PMS一样 是服务
-
SF是生产者/消费者设计,生产者:SF把每一个应用程序作为生产者生产图元保存到SF的图层里
消费者:SF作为消费者 把生产者放到SF的队列
-
为了能够跨进程,传输大容量图元数据给SF, 使用匿名共享内存,该内存作为工具,承担中转站角色,把图元数据转给cpu/gpu
-
Binder只能1M ,匿名共享内存也是只拷贝一次的通信方式
三层机制和队列
第一层(应用层)
应用层 会调用Measuer(测量) -->layout(排版)-->draw(绘制) -->生成了纹理和多边形-->栅格化操作
surface的buffer作为画板,Canvas作为画笔,draw实际没有生成图像到缓冲区,只是记录了绘制命令,然后生成了纹理和多边形。然后栅格化。
CPU :Measuer,Layout 纹理和多边形生成,发送纹理和多边形到GPU
GPU: 将CPU生成的纹理和多边形进行栅格化以及合成
第二层(SurfaceFlinger)
- 在上层作为消费者,硬件层的生产者
- 负责图像合成
- 和AMS一样是系统服务
第三层(屏幕)
SF将多个surface内容合成,然后提交到屏幕后缓冲区,等待同步信号到来,显示到屏幕上,SF会和屏幕的后缓冲区建立联系,SF起承上启下左右。
屏幕从缓冲区读取,从buffer的其实地址开始从上到下,从左到右扫描整个buffer,内容显示到屏幕上
如果只有一个buffer 同时进行读取和写入,那会出问题,所以有了双缓冲机制
Buffer的管理
- surface内部提供一个BufferQueue 和SF形成一个生产消费者模型
- 上层对应生产者,SF对应消费者。
Buffer的四种状态
-
Free 可被上层使用
-
Dequeued 出列 被上层使用
-
Queued 入列 已经完成上层绘制,等待SF的合成
-
Acquired 被获取,SF正在持有该buffer进行合成
一次完整的过程为 从BufferQueue转移到上层,上层绘制完 放回BufferQueue
SF拿去合成,用完放回BufferQueue,如此循环
双缓冲
前缓冲 用于显示内容到屏幕的帧缓冲区
后缓冲区,用于后台合成下一帧图,假设前一帧合成好,等待信号就刷新到屏幕上
前后缓冲区会不断切换