DropBox系列-安卓DropBox介绍
前言:
作者本人負責公司的APM監(jiān)控模塊,因為工作的原因,對ANR,crash等流程研究的比較多,最近在打造APM監(jiān)控平臺的時候,順帶對DropBox的實現(xiàn)原理進行了一定的學習和研究,發(fā)現(xiàn)了一些妙用,因此寫這篇文章來分享。
本系列分為兩篇文章,
1.DropBox系列-安卓DropBox介紹:主要介紹DropBox的一些實現(xiàn)原理。
2.DropBox系列-利用DropBox打造APM框架:主要介紹利用DropBox打造一個面向所有APP的穩(wěn)定性監(jiān)控框架。
PS:本文的代碼以安卓9(SDK=28)的源碼來介紹,因為目前車載開發(fā)基本上都是以安卓9為基礎來定制的,而且DropBox對于那些擁有系統(tǒng)權限的APP來講意義更大一些。
一.DropBox簡介
dropbox是安卓系統(tǒng)中用來記錄一些異常信息的模塊,比如某個應用crash了或者anr了,系統(tǒng)最終都會把記錄的異常信息記錄到dropbox中。
其一般會把異常信息記錄到中:data/system/dropbox文件夾下,記錄的類型會有很多種,主要有CRASH,ANR,墓碑日志,native崩潰等等,如下圖所示:
?
當然,由于SELinux權限的限制,這些文件夾對于普通的APP來講說不可訪問的,只有擁有系統(tǒng)簽名的APP才可以訪問的。
二.DropBox記錄流程
2.1 binder接口
DropBoxManagerService中,提供了一個binder實現(xiàn)類,主要提供了四個方法,其實最核心的,就是add方法,也就是真正實現(xiàn)記錄的方法。我們的源碼閱讀,也從這里開始。
private final IDropBoxManagerService.Stub mStub = new IDropBoxManagerService.Stub() {@Overridepublic void add(DropBoxManager.Entry entry) {DropBoxManagerService.this.add(entry);}@Overridepublic boolean isTagEnabled(String tag) {return DropBoxManagerService.this.isTagEnabled(tag);}@Overridepublic DropBoxManager.Entry getNextEntry(String tag, long millis) {return DropBoxManagerService.this.getNextEntry(tag, millis);}@Overridepublic void dump(FileDescriptor fd, PrintWriter pw, String[] args) {DropBoxManagerService.this.dump(fd, pw, args);}};2.2?add流程
binder的add方法之后,會調(diào)用到DropBoxManagerService的add方法。
其核心實現(xiàn)邏輯就是add方法,add方法主要做了一下的工作:
1.把接收到的Entry內(nèi)容寫入到臨時文件tmp中。
temp = new File(mDropBoxDir, "drop" + Thread.currentThread().getId() + ".tmp");2.寫入完成后,把tmp文件修改文件名,改成data_app_anr@111這樣的文件名。
final File file = this.getFile(dir);if (!temp.renameTo(file)) {throw new IOException("Can't rename " + temp + " to " + file);}3.切換成主線程,發(fā)送廣播。
final Intent dropboxIntent = new Intent(DropBoxManager.ACTION_DROPBOX_ENTRY_ADDED);dropboxIntent.putExtra(DropBoxManager.EXTRA_TAG, tag);dropboxIntent.putExtra(DropBoxManager.EXTRA_TIME, time);if (!mBooted) {dropboxIntent.addFlags(Intent.FLAG_RECEIVER_REGISTERED_ONLY);}// Call sendBroadcast after returning from this call to avoid deadlock. In particular// the caller may be holding the WindowManagerService lock but sendBroadcast requires a// lock in ActivityManagerService. ActivityManagerService has been caught holding that// very lock while waiting for the WindowManagerService lock.mHandler.sendMessage(mHandler.obtainMessage(MSG_SEND_BROADCAST, dropboxIntent));三.DropBox妙用
既然在系統(tǒng)發(fā)現(xiàn)異常后,會主動把對應的記錄文件進行記錄,那么,我們是不是可以利用dropbox,針對系統(tǒng)中所有的APP應用進行一個切面編程,捕獲所有的異常進行上報。這樣就不需要每個應用單獨去接入注入bugly一類的框架了,而且由于少了bugly的影響,性能,穩(wěn)定性會更好。
實現(xiàn)對dropbox的切面編程,主要有以下三個方案:
方案一:監(jiān)聽dropbox文件夾變化
利用FileObserver對data/system/dropbox文件夾進行修改監(jiān)聽,bugly其實也是用的這個原理,6.0以上會因為SELinux的權限失效。所以要對SELinux的文件夾進行配置。
方案二:修改系統(tǒng)源碼進行binder通訊
修改系統(tǒng)AMS中的源碼,APP進行binder的注冊。在發(fā)現(xiàn)崩潰或者ANR的之后,利用APP注冊的binder,通知APP一側(cè)。
方案三:利用廣播進行通知
上面介紹,保存完成后,回發(fā)送一個廣播。那么我們在APP側(cè)監(jiān)聽這個廣播,就可以知道什么時候出現(xiàn)了異常。
具體的實現(xiàn)和結(jié)果,我們下一章APM框架再來細細講解。
總結(jié)
以上是生活随笔為你收集整理的DropBox系列-安卓DropBox介绍的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: 看电影学英语的方法
- 下一篇: html实现视频会议 (web端+手机端