vsync信号源产生地
1.硬件支持
2.软件模拟
SurfaceFlinger创建的init会初始创建HWComposer
void SurfaceFlinger::init() {
mHwc = new HWComposer(this,*static_cast<HWComposer::EventHandler *>(this));
}
HWComposer::HWComposer(
const sp<SurfaceFlinger>& flinger,
EventHandler& handler)
{
bool needVSyncThread = true;
loadHwcModule();
if (mHwc) {//存在加载成功composer硬件抽象层,则用硬件支持的vSync信号
if (mHwc->registerProcs) {
mCBContext->hwc = this;
mCBContext->procs.invalidate = &hook_invalidate;
mCBContext->procs.vsync = &hook_vsync;//硬件回调的vsync信号处理函数
if (hwcHasApiVersion(mHwc, HWC_DEVICE_API_VERSION_1_1))
mCBContext->procs.hotplug = &hook_hotplug;
else
mCBContext->procs.hotplug = NULL;
memset(mCBContext->procs.zero, 0, sizeof(mCBContext->procs.zero));
mHwc->registerProcs(mHwc, &mCBContext->procs);
}
//先关闭vsync信号
needVSyncThread = false;
eventControl(HWC_DISPLAY_PRIMARY, HWC_EVENT_VSYNC, 0);
}
//软件模拟的vsync信号
if (needVSyncThread) {
mVSyncThread = new VSyncThread(*this);
}
}
void HWComposer::hook_vsync(const struct hwc_procs* procs, int disp,int64_t timestamp) {
//procs是我们传过去的,根据这个指针我们可以转化成外部的我们自己用的指针
//硬件层总是用这种技巧 一般procs作为另一个struct结构的第一成员,类似与c++中的继承关系了
cb_context* ctx = reinterpret_cast<cb_context*>(const_cast<hwc_procs_t*>(procs));
ctx->hwc->vsync(disp, timestamp);
}
void HWComposer::vsync(int disp, int64_t timestamp) {
if (uint32_t(disp) < HWC_NUM_PHYSICAL_DISPLAY_TYPES) {
//记录一下最后一次产生的vsync信号的时间值
if (timestamp == mLastHwVSync[disp]) {
return;
}
mLastHwVSync[disp] = timestamp;
//通知外面 ,mEventHandler是构造函数初始化的,就是SurfaceFlinger
//查看一下应用这个函数的地方还会找到bool HWComposer::VSyncThread::threadLoop() 这个就是
//软件模拟的vsync.
//所以不管软件还是硬件的vsync信号最后都有mEventHandler.onVSyncReceived进行处理
mEventHandler.onVSyncReceived(disp, timestamp);
}
}
HWComposer初始化后,vsync信号的输出地就是mEventHandler.onVSyncReceived (SurfaceFlinger::onVSyncReceived)
void SurfaceFlinger::onVSyncReceived(int type, nsecs_t timestamp) {
bool needsHwVsync = false;
{
Mutex::Autolock _l(mHWVsyncLock);
if (type == 0 && mPrimaryHWVsyncEnabled) {
//添加采样时间点 mPrimaryDispSync通过采样点计算出vsync信号的触发间隔和波动范围
//然后通过软件模拟出vsync信号,如果不需要采样点了就返回false,这样外部根据返回值
//开启和关闭硬件(HWComposer中产生的)vsync信号,据说可以省电
needsHwVsync = mPrimaryDispSync.addResyncSample(timestamp);
}
}
//开启关闭HWComposer的vsync
if (needsHwVsync) {
enableHardwareVsync();
} else {
disableHardwareVsync(false);
}
}
//关闭vsync
void SurfaceFlinger::disableHardwareVsync(bool makeUnavailable) {
Mutex::Autolock _l(mHWVsyncLock);
if (mPrimaryHWVsyncEnabled) {
//eventControl(HWC_DISPLAY_PRIMARY, SurfaceFlinger::EVENT_VSYNC, false);
//又是一个控制线程,线程中会调用eventControl(HWC_DISPLAY_PRIMARY
//setVsyncEnabled设置变量后激活线程
mEventControlThread->setVsyncEnabled(false);
mPrimaryDispSync.endResync();
mPrimaryHWVsyncEnabled = false;
}
if (makeUnavailable) {
mHWVsyncAvailable = false;
}
}
//开启vsync
void SurfaceFlinger::enableHardwareVsync() {
mEventControlThread->setVsync