Exoplayer: detachFromGLContext in SurfaceTexture

Created on 25 Aug 2015  路  8Comments  路  Source: google/ExoPlayer

After I updated to recent ExoPlayer version I started receiving crash reports detachFromGLContext method in SurfaceTexture. I am using TextureView to show the video content.

I am not suggesting that this is ExoPlayer bug, but 1.4.2 version is the only connection to this issue.

Here are some logs:
java.lang.RuntimeException: Error during detachFromGLContext (see logcat for details)
at android.graphics.SurfaceTexture.detachFromGLContext(SurfaceTexture.java:195)
at android.view.TextureView.destroySurface(TextureView.java:232)
at android.view.TextureView.access$000(TextureView.java:105)
at android.view.TextureView$1.run(TextureView.java:220)
at android.view.HardwareRenderer$Gl20Renderer.safelyRun(HardwareRenderer.java:2243)
at android.view.View.executeHardwareAction(View.java:12514)
at android.view.TextureView.onDetachedFromWindow(TextureView.java:217)
at android.view.View.dispatchDetachedFromWindow(View.java:12655)
at android.view.ViewGroup.dispatchDetachedFromWindow(ViewGroup.java:2587)
at android.view.ViewGroup.dispatchDetachedFromWindow(ViewGroup.java:2587)
at android.view.ViewGroup.dispatchDetachedFromWindow(ViewGroup.java:2587)
at android.view.ViewGroup.dispatchDetachedFromWindow(ViewGroup.java:2587)
at android.view.ViewGroup.removeDetachedView(ViewGroup.java:4093)
at android.widget.AbsListView.access$4700(AbsListView.java:95)
at android.widget.AbsListView$RecycleBin.pruneScrapViews(AbsListView.java:6849)
at android.widget.AbsListView$RecycleBin.scrapActiveViews(AbsListView.java:6830)
at android.widget.ListView.layoutChildren(ListView.java:1651)
at android.widget.AbsListView.onLayout(AbsListView.java:2087)
at android.view.View.layout(View.java:14857)
at android.view.ViewGroup.layout(ViewGroup.java:4643)
at android.support.v4.widget.SwipeRefreshLayout.onLayout(Unknown Source)
at android.view.View.layout(View.java:14857)
at android.view.ViewGroup.layout(ViewGroup.java:4643)
at android.support.v4.view.ViewPager.onLayout(Unknown Source)
at android.view.View.layout(View.java:14857)
at android.view.ViewGroup.layout(ViewGroup.java:4643)
at android.widget.RelativeLayout.onLayout(RelativeLayout.java:1055)
at android.view.View.layout(View.java:14857)
at android.view.ViewGroup.layout(ViewGroup.java:4643)
at android.widget.FrameLayout.layoutChildren(FrameLayout.java:453)
at android.widget.FrameLayout.onLayout(FrameLayout.java:388)
at android.view.View.layout(View.java:14857)
at android.view.ViewGroup.layout(ViewGroup.java:4643)
at android.widget.LinearLayout.setChildFrame(LinearLayout.java:1671)
at android.widget.LinearLayout.layoutVertical(LinearLayout.java:1525)
at android.widget.LinearLayout.onLayout(LinearLayout.java:1434)
at android.view.View.layout(View.java:14857)
at android.view.ViewGroup.layout(ViewGroup.java:4643)
at android.widget.FrameLayout.layoutChildren(FrameLayout.java:453)
at android.widget.FrameLayout.onLayout(FrameLayout.java:388)
at android.view.View.layout(View.java:14857)
at android.view.ViewGroup.layout(ViewGroup.java:4643)
at android.view.ViewRootImpl.performLayout(ViewRootImpl.java:2013)
at android.view.ViewRootImpl.performTraversals(ViewRootImpl.java:1770)
at android.view.ViewRootImpl.doTraversal(ViewRootImpl.java:1019)
at android.view.ViewRootImpl$TraversalRunnable.run(ViewRootImpl.java:5725)
at android.view.Choreographer$CallbackRecord.run(Choreographer.java:761)
at android.view.Choreographer.doCallbacks(Choreographer.java:574)
at android.view.Choreographer.doFrame(Choreographer.java:544)
at android.view.Choreographer$FrameDisplayEventReceiver.run(Choreographer.java:747)
at android.os.Handler.handleCallback(Handler.java:733)
at android.os.Handler.dispatchMessage(Handler.java:95)
at android.os.Looper.loop(Looper.java:136)
at android.app.ActivityThread.main(ActivityThread.java:5086)
at java.lang.reflect.Method.invokeNative(Native Method)
at java.lang.reflect.Method.invoke(Method.java:515)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:785)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:601)
at dalvik.system.NativeStart.main(Native Method)

I also found a ticket in Google Open Source Project related to this issue: https://code.google.com/p/android/issues/detail?id=181511 but it didn't receive any attention yet.

They are suggesting that the crash is happening in paused mode, when the texturesurface is detached from the view.

Do you have suggestion or recommendations?

Thanks a lot!

need more info

Most helpful comment

The point is, TextureView must own an unreleased SurfaceTexture to release in onDetachedFromWindow() before 4.4

So, the workaround could be like this:

  1. Make a wrapper to hold SurfaceTexture
    https://github.com/Bilibili/ijkplayer/blob/188ee8039a16da1ef269498f4af6e88fb427fdec/android/ijkplayer/ijkplayer-example/src/main/java/tv/danmaku/ijk/media/example/widget/media/TextureRenderView.java#L85
  2. Make a wrapper to hold MediaPlayer
    https://github.com/Bilibili/ijkplayer/blob/188ee8039a16da1ef269498f4af6e88fb427fdec/android/ijkplayer/ijkplayer-java/src/main/java/tv/danmaku/ijk/media/player/TextureMediaPlayer.java#L34
  3. Transfer SurfaceTexture's ownership back to TextureView, and let onSurfaceTextureDestroyed() returns true, if MediaPlayer is released before TextureView.detachFromWindow(),
    https://github.com/Bilibili/ijkplayer/blob/188ee8039a16da1ef269498f4af6e88fb427fdec/android/ijkplayer/ijkplayer-example/src/main/java/tv/danmaku/ijk/media/example/widget/media/TextureRenderView.java#L307
  4. It's also OK to return false from onSurfaceTextureDestroyed(), if you'd like to own SurfaceTexture longer. But Make sure only release SurfaceTexture after onDetachedFromWindow().

All 8 comments

Was ExoPlayer really the only thing that changed when you upgraded, or did some of your application code change as well? This is pretty unlikely to be directly related to ExoPlayer, in my opinion.

Pretty confident this is a TextureView issue. We've been getting it for years running a VideoView port that extends TextureView instead of SurfaceView

Also it's 99% Android 4 for us, even though we're 60% Kitkat daily users so this should go away

@edikfuks @ryango Did you guys ever solve this? I'm currently seeing it on Android 4.1.x and below using TextureView.

Never did. Think it's a platform issue.

I'm seeing this issue too and I agree with @ryango, its a platform issue specific to 4.4 and before.

After 4.4 the problematic call to detachFromGLContext was removed. See diff for
TextureVIew commit 19b6bcf.

The point is, TextureView must own an unreleased SurfaceTexture to release in onDetachedFromWindow() before 4.4

So, the workaround could be like this:

  1. Make a wrapper to hold SurfaceTexture
    https://github.com/Bilibili/ijkplayer/blob/188ee8039a16da1ef269498f4af6e88fb427fdec/android/ijkplayer/ijkplayer-example/src/main/java/tv/danmaku/ijk/media/example/widget/media/TextureRenderView.java#L85
  2. Make a wrapper to hold MediaPlayer
    https://github.com/Bilibili/ijkplayer/blob/188ee8039a16da1ef269498f4af6e88fb427fdec/android/ijkplayer/ijkplayer-java/src/main/java/tv/danmaku/ijk/media/player/TextureMediaPlayer.java#L34
  3. Transfer SurfaceTexture's ownership back to TextureView, and let onSurfaceTextureDestroyed() returns true, if MediaPlayer is released before TextureView.detachFromWindow(),
    https://github.com/Bilibili/ijkplayer/blob/188ee8039a16da1ef269498f4af6e88fb427fdec/android/ijkplayer/ijkplayer-example/src/main/java/tv/danmaku/ijk/media/example/widget/media/TextureRenderView.java#L307
  4. It's also OK to return false from onSurfaceTextureDestroyed(), if you'd like to own SurfaceTexture longer. But Make sure only release SurfaceTexture after onDetachedFromWindow().

I was also experiencing that problem when using TextureView with MediaPlayer on Android 6.0.1 on (D722) and Android Nougat on Nexus 5X and fixed it with workaround pt. 4 from @bbcallen comment:

It's also OK to return false from onSurfaceTextureDestroyed(), if you'd like to own SurfaceTexture longer. But Make sure only release SurfaceTexture after onDetachedFromWindow().

So that's not problem which was resolved in 4.4, but for me it was throwing NPE in dispatchDetachedFromWindow() during removing of fragment which contained TextureView's in it's layout

Was this page helpful?
0 / 5 - 0 ratings