ReleaseonTrimMemoryListener after ImageReaderSurfaceProducer released. (flutter/engine#55760)

Fixes https://github.com/flutter/flutter/issues/156434.

A better fix for the workaround in https://github.com/flutter/flutter/issues/156158.

This should likely be cherrypicked, as it's a memory leak, safe, and avoids workaround code in plugins.
This commit is contained in:
Matan Lurey 2024-10-08 18:35:17 -07:00 committed by GitHub
parent e118869e40
commit 8e3b58f166
2 changed files with 26 additions and 3 deletions

View File

@ -705,6 +705,7 @@ public class FlutterRenderer implements TextureRegistry {
private void releaseInternal() {
cleanup();
released = true;
removeOnTrimMemoryListener(this);
imageReaderProducers.remove(this);
}

View File

@ -4,6 +4,7 @@
package io.flutter.embedding.engine.renderer;
import static android.content.ComponentCallbacks2.TRIM_MEMORY_BACKGROUND;
import static android.content.ComponentCallbacks2.TRIM_MEMORY_COMPLETE;
import static org.junit.Assert.assertArrayEquals;
import static org.junit.Assert.assertEquals;
@ -671,7 +672,7 @@ public class FlutterRendererTest {
// Invoke the onTrimMemory callback with level 40.
// This should result in a trim.
texture.onTrimMemory(40);
texture.onTrimMemory(TRIM_MEMORY_BACKGROUND);
shadowOf(Looper.getMainLooper()).idle();
assertEquals(0, texture.numImageReaders());
@ -769,12 +770,33 @@ public class FlutterRendererTest {
producer.setCallback(callback);
// Trim memory.
((FlutterRenderer.ImageReaderSurfaceProducer) producer).onTrimMemory(40);
flutterRenderer.onTrimMemory(TRIM_MEMORY_BACKGROUND);
// Verify.
verify(callback).onSurfaceDestroyed();
}
@Test
public void ImageReaderSurfaceProducerUnsubscribesWhenReleased() {
// Regression test for https://github.com/flutter/flutter/issues/156434.
FlutterRenderer flutterRenderer = engineRule.getFlutterEngine().getRenderer();
TextureRegistry.SurfaceProducer producer = flutterRenderer.createSurfaceProducer();
// Create and set a mock callback.
TextureRegistry.SurfaceProducer.Callback callback =
mock(TextureRegistry.SurfaceProducer.Callback.class);
producer.setCallback(callback);
// Release the surface.
producer.release();
// Call trim memory.
flutterRenderer.onTrimMemory(TRIM_MEMORY_BACKGROUND);
// Verify was not called.
verify(callback, never()).onSurfaceDestroyed();
}
@Test
public void ImageReaderSurfaceProducerIsCreatedOnLifecycleResume() throws Exception {
FlutterRenderer flutterRenderer = engineRule.getFlutterEngine().getRenderer();
@ -795,7 +817,7 @@ public class FlutterRendererTest {
producer.setCallback(callback);
// Trim memory.
((FlutterRenderer.ImageReaderSurfaceProducer) producer).onTrimMemory(40);
flutterRenderer.onTrimMemory(TRIM_MEMORY_BACKGROUND);
// Trigger a resume.
((LifecycleRegistry) ProcessLifecycleOwner.get().getLifecycle())