日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

内存泄露(十)-- KOOM(高性能线上内存监控方案)

發(fā)布時間:2024/1/18 编程问答 40 豆豆
生活随笔 收集整理的這篇文章主要介紹了 内存泄露(十)-- KOOM(高性能线上内存监控方案) 小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.

KOOM介紹
OOMMonitor 介紹
KOOM線上APM監(jiān)控最全剖析
一文看懂快手KOOM高性能監(jiān)控方案
KOOM 淺析
【開源庫剖析】KOOM V1.0.5 源碼解析

目錄

  • KOOM 功能
    • 1. Java Heap 泄漏監(jiān)控
      • 1.1 OOMMonitor 介紹
      • 1.2 OOMMonitor 適用范圍
      • 1.3 OOMMonitor 接入
    • 2. Native Heap 泄漏監(jiān)控
      • 2.1 LeakMonitor 介紹
      • 2.2 LeakMonitor 適用范圍
      • 2.3 LeakMonitor 接入
    • 3. Thread 泄漏監(jiān)控
      • 3.1 ThreadLeakMonitor 介紹
      • 3.2 ThreadLeakMonitor 適用范圍
      • 3.3 ThreadLeakMonitor 接入

??KOOM(Kwai OOM, Kill OOM)是快手性能優(yōu)化團隊在處理移動端OOM問題的過程中沉淀出的一套完整解決方案。

KOOM 功能

Koom流程:

OOM問題原因分類

  • Java堆內存溢出
  • 無足夠連續(xù)內存空間
  • FD(文件描述符)超出限制
  • 線程數(shù)量超出限制
  • 虛擬內存不足
  • 1. Java Heap 泄漏監(jiān)控

    ??koom-java-leak 模塊用于 Java Heap 泄漏監(jiān)控:它利用 Copy-on-write 機制 fork 子進程 dump Java Heap,解決了 dump 過程中 app 長時間凍結的問題

    • fork子進程去執(zhí)行dumpHprofData方法
    • fork進程采用的是“Copy On Write”技術,只有在進行寫入操作時,才會為子進程拷貝分配獨立的內存空間,默認情況下,子進程可以和父進程共享同個內存空間,所以,當我們要執(zhí)行dumpHprofData方法時,可以先fork一個子進程,它擁有父進程的內存副本,然后在子進程中執(zhí)行dumpHprofData方法,而父進程則可以正常繼續(xù)運行。

      ??hprof是基于JVMTI實現(xiàn)的內存分析器代理,其轉儲文件記錄了Java的內存鏡像(Heap Profile),其中記錄了內存堆詳細的使用信息,可用于分析Java程序內存的各種性能問題。
      ??虛擬機提供的Debug.dumpHprofData可以將hprof文件輸出在指定的文件中,但是這個過程會“凍結”整個應用進程,造成數(shù)秒甚至數(shù)十秒內用戶無法操作,即dump文件也是會產生STW(Stop the world),跟GC一樣會讓所有線程掛起。

    HeapMonitor.java

    public boolean isTrigger() {if (!started) {return false;}HeapStatus heapStatus = currentHeapStatus();if (heapStatus.isOverMaxThreshold) {// 已達到最大閥值,強制觸發(fā)trigger,防止后續(xù)出現(xiàn)大內存分配導致OOM進程Crash,無法觸發(fā)triggerKLog.i(TAG, "heap used is over max ratio, force trigger and over times reset to 0");currentTimes = 0;return true;}if (heapStatus.isOverThreshold) {KLog.i(TAG, "heap status used:" + heapStatus.used / KConstants.Bytes.MB+ ", max:" + heapStatus.max / KConstants.Bytes.MB+ ", last over times:" + currentTimes);if (heapThreshold.ascending()) {// 第一次進來 或者 當前內存占用率跟上次高 或者 當前內存占用率超過了最大的閾值(95%)if (lastHeapStatus == null || heapStatus.used >= lastHeapStatus.used || heapStatus.isOverMaxThreshold) {currentTimes++;} else {KLog.i(TAG, "heap status used is not ascending, and over times reset to 0");currentTimes = 0;}} else {currentTimes++;}} else {currentTimes = 0;}lastHeapStatus = heapStatus;return currentTimes >= heapThreshold.overTimes();}

    Koom中設置了五種檢測器
    ① HeapOOMTracker
    ② ThreadOOMTracker
    ③ FdOOMTracker
    ④ PhysicalMemoryOOMTracker
    ⑤ FastHugeMemoryOOMTracker
    前三種稱為長期高內存檢測器,檢測機制是當計算出內存占用率之后,我們看下面的一個判斷條件,如果內存占用率超過我們設定的一個閾值(例如0.8),而且當前內存占用率跟上次比較超過了千分之5,那么mOverThresholdCount變量就會自增1。

    Heap監(jiān)測機制是第一次進來 或者 當前內存占用率跟上次高 或者
    當前內存占用率超過了最大的閾值(95%),三個條件只要滿足一個,那么mOverThresholdCount變量就會自增1

    ??因為檢測是一個循環(huán)的過程,所以當?shù)谝淮芜M來的時候,一定會自增1,而且會將本次的內存占用率賦值給mLastHeapRatio,當下次進來的時候,如果內存占用率較上次降低了,那么就會重置。
    ??如此往復,當mOverThresholdCount超出我們設置的閾值(例如3次),我們就認定系統(tǒng)發(fā)生了內存泄漏,這個時候就需要告警,并dump內存快照分析問題。
    1)內存占用超過80%,2)并且檢測到了3次,兩個條件同時滿足就會進行dump。
    第四種代碼中返回false沒有進行處理。
    第五種稱為高危內存與快速增長檢測器,檢測機制是內存占用超過90%或者本次檢測與上次檢測內存占用超過350M,滿足兩個條件之一就會進行dump。

    1.1 OOMMonitor 介紹

    用于監(jiān)控應用的 Java 內存泄漏問題,它的核心原理:

    • 周期性查詢Java堆內存、線程數(shù)、文件描述符數(shù)等資源占用情況,當連續(xù)多次超過設定閾值或突發(fā)性連續(xù)快速突破高閾值時,觸發(fā)鏡像采集
    • 鏡像采集采用虛擬機supend->fork虛擬機進程->虛擬機resume->dump內存鏡像的策略,將傳統(tǒng)Dump凍結進程20s的時間縮減至20ms以內
    • 基于shark執(zhí)行鏡像解析,并針對shark做了一系列調整用于提升性能,在手機設備測即可執(zhí)行離線內存泄露判定與引用鏈查找,生成分析報告

    1.2 OOMMonitor 適用范圍

    • Android L 及以上(API level >= 21)

    • 支持 armeabi-v7a arm64-v8a x86 x86-64

    1.3 OOMMonitor 接入

    OOMMonitor 接入

    2. Native Heap 泄漏監(jiān)控

    ??koom-native-leak 模塊用于 Native Heap 泄漏監(jiān)控:它利用 Tracing garbage collection 機制分析整個 Native Heap,直接輸出泄漏內存信息「大小、分配堆棧等』;極大的降低了業(yè)務同學分析、解決內存泄漏的成本。

    思路總結:

    • hook malloc/free等內存分配器方法,用于記錄Native內存分配元數(shù)據(jù)[大小、堆棧、地址等]–使用了愛奇藝的xhook庫
    • 周期性的使用mark-and-sweep分析整個進程Native Heap, 獲取不可達的內存塊信息[地址、大小]–使用到google的libmemunreachable庫
    • 利用不可達的內存塊的地址、大小等從我們記錄的元數(shù)據(jù)中獲取其分配堆棧,產出泄漏數(shù)據(jù)[不可達內存地址、大小、分配堆棧等]

    2.1 LeakMonitor 介紹

    用于監(jiān)控應用的 Native 內存泄漏問題,它的核心原理如下:

    • hook malloc/free 等內存分配器方法,用于記錄 Native 內存分配元數(shù)據(jù)「大小、堆棧、地址等」
    • 周期性的使用 mark-and-sweep 分析整個進程 Native Heap,獲取不可達的內存塊信息「地址、大小」
    • 利用不可達的內存塊的地址、大小等從我們記錄的元數(shù)據(jù)中獲取其分配堆棧,產出泄漏數(shù)據(jù)「不可達內存塊地址、大小、分配堆棧等」

    2.2 LeakMonitor 適用范圍

    • Android N 及以上(API level >= 24)
    • 僅支持 arm64-v8a

    2.3 LeakMonitor 接入

    LeakMonitor 接入

    3. Thread 泄漏監(jiān)控

    ??koom-thread-leak 模塊用于 Thread 泄漏監(jiān)控:它會 hook 線程的生命周期函數(shù),周期性的上報泄漏線程信息。

    3.1 ThreadLeakMonitor 介紹

    用于監(jiān)控應用的線程泄漏問題,它的核心原理:

    • hook pthread_create/pthread_exit 等線程方法,用于記錄線程的生命周期和創(chuàng)建堆棧,名稱等信息
    • 當發(fā)現(xiàn)一個joinable的線程在沒有detach或者join的情況下,執(zhí)行了pthread_exit,則記錄下泄露線程信息
    • 當線程泄露時間到達配置設置的延遲期限的時候,上報線程泄露信息

    3.2 ThreadLeakMonitor 適用范圍

    • Android N 及以上(API level >= 24)
    • 僅支持 arm64-v8a

    3.3 ThreadLeakMonitor 接入

    ThreadLeakMonitor 接入

    總結

    以上是生活随笔為你收集整理的内存泄露(十)-- KOOM(高性能线上内存监控方案)的全部內容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網(wǎng)站內容還不錯,歡迎將生活随笔推薦給好友。