自 2025 年 3 月 27 日起,我们建议您使用 android-latest-release
而非 aosp-main
构建 AOSP 并为其做出贡献。如需了解详情,请参阅 AOSP 的变更。
客户端帧缓冲区管理
使用集合让一切井井有条
根据您的偏好保存内容并对其进行分类。
从 Android 13 开始,每当屏幕分辨率发生变化时,系统都会分配在客户端合成期间使用的新的帧缓冲区。分辨率变化后,SurfaceFlinger 会对下一个“失效”周期执行此分配。invalidate
分辨率切换期间的帧缓冲区管理
分辨率会由于以下两种情况之一而发生变化:
为了避免出现灾难性问题(如内存碎片化),在没有为新旧帧缓冲区预留足够内存的设备上,HWC 必须停止使用旧帧缓冲区并释放这些帧缓冲区的所有句柄,如下所示:
释放句柄会导致帧缓冲区内存会被完全取消分配,SurfaceFlinger 无法在下一个“失效”周期内执行新帧缓冲区分配。invalidate
帧缓冲区管理建议
如果 HWC 未及时释放旧帧缓冲区的句柄,则新的帧缓冲区分配会在旧的帧缓冲区取消分配之前发生。如果新的帧缓冲区的分配因碎片化或其他问题而失败,上述情况可能会导致灾难性问题。更糟糕的是,如果 HWC 没有释放任何句柄,还可能会发生内存泄漏。
为避免发生灾难性的分配失败问题,请遵循以下建议:
如果 HWC 需要继续使用旧的客户端帧缓冲区,直到提供了新的客户端帧缓冲区,那么为新旧帧缓冲区都预留足够的内存至关重要,并可能需要对帧缓冲区内存空间运行碎片整理算法。
为独立于其余图形内存缓冲区的帧缓冲区分配一个专属的内存池。这一点很重要,因为在取消分配和重新分配帧缓冲区期间,第三方进程可以尝试分配显存。如果帧缓冲区使用了同一显存池,而且显存已满,则第三方进程可以占用帧缓冲区先前分配的显存,从而导致没有足够的内存供帧缓冲区重新分配,或可能导致内存空间碎片化。
测试帧缓冲区管理
建议 OEM 针对其设备的分辨率切换测试客户端帧缓冲区内存管理是否正常,如下所述:
本页面上的内容和代码示例受内容许可部分所述许可的限制。Java 和 OpenJDK 是 Oracle 和/或其关联公司的注册商标。
最后更新时间 (UTC):2025-04-04。
[null,null,["最后更新时间 (UTC):2025-04-04。"],[],[],null,["# Client framebuffer management\n\nStarting with Android 13, new framebuffers, used during\n[client](https://android.googlesource.com/platform/hardware/interfaces/+/refs/heads/android16-release/graphics/composer/aidl/android/hardware/graphics/composer3/DisplayCommand.aidl#113)\ncomposition, are allocated whenever the display resolution changes. This\nallocation is performed by SurfaceFlinger on the next *invalidate* cycle\nafter a resolution change.\n\nFramebuffer management during resolution switches\n-------------------------------------------------\n\nResolution changes occur due to one of the following\ntwo scenarios:\n\n- A [hotplug event](https://android.googlesource.com/platform/hardware/interfaces/+/refs/heads/android16-release/graphics/composer/aidl/android/hardware/graphics/composer3/IComposerCallback.aidl#41),\n initiated by Hardware Composer (HWC), which occurs when swapping from one external\n display to a different external display that has a different default resolution.\n\n During a hotplug event, the handles to the old framebuffers are released\n when the old display data is deallocated.\n- A display mode switch initiated by SurfaceFlinger, which occurs when the\n user changes the resolution with [user settings](https://android.googlesource.com/platform/frameworks/base/+/refs/heads/android16-release/core/java/android/hardware/display/DisplayManager.java#1209),\n or an app changes the resolution with [`preferredDisplayModeId`](https://developer.android.com/reference/android/view/WindowManager.LayoutParams#preferredDisplayModeId).\n\n During a display mode switch, the handles to existing client framebuffers\n are released by SurfaceFlinger before calling [`setActiveConfig`](https://android.googlesource.com/platform/hardware/interfaces/+/refs/heads/android16-release/graphics/composer/aidl/android/hardware/graphics/composer3/IComposerClient.aidl#550)\n or [`setActiveConfigWithConstraints`](https://android.googlesource.com/platform/hardware/interfaces/+/refs/heads/android16-release/graphics/composer/aidl/android/hardware/graphics/composer3/IComposerClient.aidl#577).\n\nTo avoid catastrophic problems, such as memory fragmentation, on devices that\ndon't reserve enough memory for the old and new framebuffers, it's critical\nthat HWC ceases to use the old framebuffers and releases any\nhandles to these framebuffers as shown in the following cases:\n\n- For hotplug events, immediately before calling [`onHotplug`](https://android.googlesource.com/platform/hardware/interfaces/+/refs/heads/android16-release/graphics/composer/aidl/android/hardware/graphics/composer3/IComposerCallback.aidl#41).\n\n- For mode switches, immediately after the call to [`setActiveConfig`](https://android.googlesource.com/platform/hardware/interfaces/+/refs/heads/android16-release/graphics/composer/aidl/android/hardware/graphics/composer3/IComposerClient.aidl#550)\n or [`setActiveConfigWithConstraints`](https://android.googlesource.com/platform/hardware/interfaces/+/refs/heads/android16-release/graphics/composer/aidl/android/hardware/graphics/composer3/IComposerClient.aidl#577).\n\nReleasing the handles allows the framebuffer memory to be fully deallocated\nprior to the allocation of new framebuffers that SurfaceFlinger performs\nduring the next *invalidate* cycle.\n\n### Recommendations for framebuffer management\n\nIf HWC doesn't release handles to old framebuffers in time,\nthe new framebuffer allocation takes place before the old framebuffer\ndeallocation. This can cause catastrophic problems when the new allocation fails\ndue to fragmentation or other issues. Even worse, if\nHWC doesn't release these handles at all, a memory leak can\noccur.\n\nTo avoid catastrophic allocation failures, follow these recommendations:\n\n- If HWC needs to continue using the old client framebuffers until the new\n client framebuffers are provided, then it's critical to reserve enough memory\n for both the old and new framebuffers, and possibly run defragmentation\n algorithms on the framebuffer memory space.\n\n- Allocate a dedicated memory pool for the framebuffers that's separate from\n the rest of the graphic buffer memory. This is important because between\n deallocation and reallocation of the framebuffers, a third-party process can\n attempt to allocate graphics memory. If the same graphics memory pool is\n used by the framebuffer and if the graphics memory is full, the third-party\n process can occupy the graphics memory previously allocated by a framebuffer,\n thus leaving insufficient memory for the framebuffer reallocation or, possibly\n fragmenting the memory space.\n\nTest framebuffer management\n---------------------------\n\nOEMs are advised to test for proper client framebuffer memory management across\nresolution switches for their device, described as follows:\n\n- For hotplug events, simply unplug and reconnect two different displays with\n different resolutions.\n\n- For mode switches, use the [`ModeSwitchingTestActivity`](https://cs.android.com/android/platform/superproject/+/android-latest-release:cts/apps/CtsVerifier/src/com/android/cts/verifier/tv/display/ModeSwitchingTestActivity.java;l=47-53;drc=c80d948aff1e7df5c2dc0ddba0d1cd63a90e4d9c) CTS\n Verifier test to initiate a mode switch for testing framebuffer memory behavior.\n This test can visually identify problems that are hard to detect\n programmatically."]]