android graphic(9)—开发者选项关闭HW overlays
2016-02-22 17:18
429 查看
setting相关代码
surface flinger处理1008 code
在开发者选项中,有许多关于图形的debug选项,今天研究之下,加深了对binder的使用。下面以关闭HW oveylays为例,也就是强制使用GLES去对图层进行合成,而不使用oveylays。
进而去调用writeDisableOverlaysOption(),
在前面的文章《android graphic(3)—surfaceflinger的启动流程》 中介绍过,虽然surfaceflinger向service manager注册的时候用的是SurfaceFlinger的名字,但是一般都是通过ComposerService这个Singleton单例去使用,SurfaceFlinger继承自BnSurfaceComposer。
上面writeDisableOverlaysOption()函数主要包括2部分(虽然在java层,没有native中的BpBinder,BBinder等,但是和c++中的思路是一致的,下面用带引号的BpBinder去表示java中的代理对象):
1.获取SurfaceFlinger服务对应的“BpBinder”;
2.直接使用“BpBinder”去transact。
前面在介绍service时,一般使用“BpBinder”时,都会先将“BpBinder”interface_cast成对应的“BpXXX”,然后调用“BpXXX”的接口,但其接口一般都是调用remote()->transact,而remote返回的也就是“BpBinder”,所以完全能直接使用BpBinder的remote函数去传输数据。在updateFlingerOptions()函数的注释中有一句“magic communication with surface flinger”,和surface flinger的神奇通信,其实就是使用了非常规方法。
上面的函数主要包括3部分:
1.对于一些code,需要去检查权限;
2.首先调用BnSurfaceComposer的onTransact,里面都是ISurfaceComposer接口中函数的实现;
3.如果onTransact()返回UNKNOWN_TRANSACTION,或者PERMISSION_DENIED,执行下面的特殊code,对于1008这种code,肯定是返回UNKNOWN_TRANSACTION,这里SurfaceFlinger做了特殊处理。而真正的处理只是设置了mDebugDisableHWC这个关闭overlays的开关。
开发者选项中还有很多类似1008这种code的使用情景,对SurfaceFlinger的调试提供了更多的手段。
surface flinger处理1008 code
在开发者选项中,有许多关于图形的debug选项,今天研究之下,加深了对binder的使用。下面以关闭HW oveylays为例,也就是强制使用GLES去对图层进行合成,而不使用oveylays。
setting相关代码
首先分析上层setting中的代码,在packages\apps\Settings\src\com\android\settings\DevelopmentSettings.java中,设置了触发函数,
public boolean onPreferenceTreeClick(PreferenceScreen preferenceScreen, Preference preference) { else if (preference == mDisableOverlays) { writeDisableOverlaysOption(); } }
进而去调用writeDisableOverlaysOption(),
private void writeDisableOverlaysOption() { try { //① 获取SurfaceFlinger对应的BpBinder IBinder flinger = ServiceManager.getService("SurfaceFlinger"); if (flinger != null) { Parcel data = Parcel.obtain(); data.writeInterfaceToken("android.ui.ISurfaceComposer"); //选择了就是关闭overlays final int disableOverlays = mDisableOverlays.isChecked() ? 1 : 0; data.writeInt(disableOverlays); //② BpBinder传的code为1008,肯定server端要实现这个1008对应的函数吧 flinger.transact(1008, data, null, 0); data.recycle(); // updateFlingerOptions(); } } catch (RemoteException ex) { } }
在前面的文章《android graphic(3)—surfaceflinger的启动流程》 中介绍过,虽然surfaceflinger向service manager注册的时候用的是SurfaceFlinger的名字,但是一般都是通过ComposerService这个Singleton单例去使用,SurfaceFlinger继承自BnSurfaceComposer。
上面writeDisableOverlaysOption()函数主要包括2部分(虽然在java层,没有native中的BpBinder,BBinder等,但是和c++中的思路是一致的,下面用带引号的BpBinder去表示java中的代理对象):
1.获取SurfaceFlinger服务对应的“BpBinder”;
2.直接使用“BpBinder”去transact。
前面在介绍service时,一般使用“BpBinder”时,都会先将“BpBinder”interface_cast成对应的“BpXXX”,然后调用“BpXXX”的接口,但其接口一般都是调用remote()->transact,而remote返回的也就是“BpBinder”,所以完全能直接使用BpBinder的remote函数去传输数据。在updateFlingerOptions()函数的注释中有一句“magic communication with surface flinger”,和surface flinger的神奇通信,其实就是使用了非常规方法。
surface flinger处理1008 code
下面我们看看server端是如何处理这个1008的code的,首先会执行server端的onTransact函数,本来是要去执行BnSurfaceComposer的onTransact函数,但是SurfaceFlinger重写了onTransact函数,因此会去执行SurfaceFlinger的onTransact函数,status_t SurfaceFlinger::onTransact( uint32_t code, const Parcel& data, Parcel* reply, uint32_t flags) { // ① 首先根据一些code,检查权限 switch (code) { case CREATE_CONNECTION: case CREATE_DISPLAY: case SET_TRANSACTION_STATE: case BOOT_FINISHED: case BLANK: case UNBLANK: { // codes that require permission check IPCThreadState* ipc = IPCThreadState::self(); const int pid = ipc->getCallingPid(); const int uid = ipc->getCallingUid(); if ((uid != AID_GRAPHICS) && !PermissionCache::checkPermission(sAccessSurfaceFlinger, pid, uid)) { ALOGE("Permission Denial: " "can't access SurfaceFlinger pid=%d, uid=%d", pid, uid); return PERMISSION_DENIED; } break; } case CAPTURE_SCREEN: { // codes that require permission check IPCThreadState* ipc = IPCThreadState::self(); const int pid = ipc->getCallingPid(); const int uid = ipc->getCallingUid(); if ((uid != AID_GRAPHICS) && !PermissionCache::checkPermission(sReadFramebuffer, pid, uid)) { ALOGE("Permission Denial: " "can't read framebuffer pid=%d, uid=%d", pid, uid); return PERMISSION_DENIED; } break; } } //② 首先调用BnSurfaceComposer的onTransact,里面都是ISurfaceComposer接口中函数 //的实现 status_t err = BnSurfaceComposer::onTransact(code, data, reply, flags); //③ 如果返回UNKNOWN_TRANSACTION,或者PERMISSION_DENIED,执行下面的特殊code // 对于1008这种code,肯定是返回UNKNOWN_TRANSACTION,这里SurfaceFlinger做了特殊处理 if (err == UNKNOWN_TRANSACTION || err == PERMISSION_DENIED) { CHECK_INTERFACE(ISurfaceComposer, data, reply); if int n; switch (code) { case 1008: // toggle use of hw composer n = data.readInt32(); //③ 从binder读出来是否关闭,设置mDebugDisableHWC mDebugDisableHWC = n ? 1 : 0; invalidateHwcGeometry(); repaintEverything(); return NO_ERROR; }
上面的函数主要包括3部分:
1.对于一些code,需要去检查权限;
2.首先调用BnSurfaceComposer的onTransact,里面都是ISurfaceComposer接口中函数的实现;
3.如果onTransact()返回UNKNOWN_TRANSACTION,或者PERMISSION_DENIED,执行下面的特殊code,对于1008这种code,肯定是返回UNKNOWN_TRANSACTION,这里SurfaceFlinger做了特殊处理。而真正的处理只是设置了mDebugDisableHWC这个关闭overlays的开关。
开发者选项中还有很多类似1008这种code的使用情景,对SurfaceFlinger的调试提供了更多的手段。
相关文章推荐
- Android Service完全解析,关于服务你所需知道的一切(下)
- Android应用开发经常使用知识
- Android之进程通讯——广播
- Android 6.0 开发者对系统权限的使用与练习(Permissions Best Practices)
- android跨进程启动service
- popupwindow全屏幕显示被状态栏挡住如何解决+Android获取状态栏高度
- Android 6.0 系统棉花糖新的特性和功能
- ANDROID_MARS学习笔记_S05_006_距离传感器
- ANDROID_MARS学习笔记_S05_005_方向传感器
- Android自定义view-弹性ScrollView(下)
- android动画ppt整理
- Android studio reset adb操作
- Android GridView控件
- 是谁制造了混乱
- ANDROID_MARS学习笔记_S05_004_过滤杂质,得到真正的加速度
- 我的Android进阶之旅------>Java文件大小转换工具类 (B,KB,MB,GB,TB,PB之间的大小转换)
- 如何获取view.setBackgroundResource里参数的int值
- Android开发之内存管理
- ubuntu运行android studio出错unable to run mksdcard sdk
- Android-下拉刷新