java.lang.IllegalStateException: Unbalanced enter/exit
See original GitHub issueVersion: 3.9.0
I was investigating a resource leak in Glide which involves lots of parallel requests and adding an try/finally/close in okhttp3.Callback.onResponse
:
@Override
public void onResponse(Call call, Response response) throws IOException {
try {
responseBody = response.body();
if (response.isSuccessful()) {
long contentLength = responseBody.contentLength();
stream = ContentLengthInputStream.obtain(responseBody.byteStream(), contentLength);
callback.onDataReady(stream);
} else {
callback.onLoadFailed(new HttpException(response.message(), response.code()));
}
} finally {
response.body().close();
}
}
After a fair amount of scrolling back and forth in Glide’s sample app (producing lots of requests and cancellations), I’ve see this exactly once:
09-10 09:44:32.588 E/AndroidRuntime( 4423): FATAL EXCEPTION: OkHttp Dispatcher
09-10 09:44:32.588 E/AndroidRuntime( 4423): Process: com.bumptech.glide.samples.flickr, PID: 4423
09-10 09:44:32.588 E/AndroidRuntime( 4423): java.lang.IllegalStateException: Unbalanced enter/exit
09-10 09:44:32.588 E/AndroidRuntime( 4423): at okio.AsyncTimeout.enter(AsyncTimeout.java:73)
09-10 09:44:32.588 E/AndroidRuntime( 4423): at okio.AsyncTimeout$2.read(AsyncTimeout.java:235)
09-10 09:44:32.588 E/AndroidRuntime( 4423): at okio.RealBufferedSource.read(RealBufferedSource.java:46)
09-10 09:44:32.588 E/AndroidRuntime( 4423): at okhttp3.internal.http1.Http1Codec$AbstractSource.read(Http1Codec.java:352)
09-10 09:44:32.588 E/AndroidRuntime( 4423): at okhttp3.internal.http1.Http1Codec$FixedLengthSource.read(Http1Codec.java:396)
09-10 09:44:32.588 E/AndroidRuntime( 4423): at okhttp3.internal.Util.skipAll(Util.java:175)
09-10 09:44:32.588 E/AndroidRuntime( 4423): at okhttp3.internal.Util.discard(Util.java:157)
09-10 09:44:32.588 E/AndroidRuntime( 4423): at okhttp3.internal.http1.Http1Codec$FixedLengthSource.close(Http1Codec.java:413)
09-10 09:44:32.588 E/AndroidRuntime( 4423): at okio.RealBufferedSource.close(RealBufferedSource.java:455)
09-10 09:44:32.588 E/AndroidRuntime( 4423): at okhttp3.internal.Util.closeQuietly(Util.java:110)
09-10 09:44:32.588 E/AndroidRuntime( 4423): at okhttp3.ResponseBody.close(ResponseBody.java:187)
09-10 09:44:32.588 E/AndroidRuntime( 4423): at com.bumptech.glide.integration.okhttp3.OkHttpStreamFetcher.onResponse(OkHttpStreamFetcher.java:111)
09-10 09:44:32.588 E/AndroidRuntime( 4423): at okhttp3.RealCall$AsyncCall.execute(RealCall.java:153)
09-10 09:44:32.588 E/AndroidRuntime( 4423): at okhttp3.internal.NamedRunnable.run(NamedRunnable.java:32)
09-10 09:44:32.588 E/AndroidRuntime( 4423): at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1133)
09-10 09:44:32.588 E/AndroidRuntime( 4423): at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:607)
09-10 09:44:32.588 E/AndroidRuntime( 4423): at java.lang.Thread.run(Thread.java:761)
09-10 09:44:32.594 W/ActivityManager( 1702): Force finishing activity com.bumptech.glide.samples.flickr/.FlickrSearchActivity
The close in onResponse
above causes lots of additional exceptions on other threads because Glide tries to read the ResponseBody
’s InputStream
after that point. The try/finally above is only there to help me debug the resource leak. However, it does produce lots of exceptions on background threads, if it’s relevant:
09-10 09:50:35.082 I/Glide ( 4511): java.io.IOException: closed
09-10 09:50:35.082 I/Glide ( 4511): at okio.RealBufferedSource$1.read(RealBufferedSource.java:426)
09-10 09:50:35.082 I/Glide ( 4511): at java.io.FilterInputStream.read(FilterInputStream.java:133)
09-10 09:50:35.082 I/Glide ( 4511): at com.bumptech.glide.util.ContentLengthInputStream.read(ContentLengthInputStream.java:66)
09-10 09:50:35.082 I/Glide ( 4511): at com.bumptech.glide.load.resource.bitmap.RecyclableBufferedInputStream.fillbuf(RecyclableBufferedInputStream.java:176)
09-10 09:50:35.082 I/Glide ( 4511): at com.bumptech.glide.load.resource.bitmap.RecyclableBufferedInputStream.read(RecyclableBufferedInputStream.java:309)
09-10 09:50:35.082 I/Glide ( 4511): at com.bumptech.glide.util.ExceptionCatchingInputStream.read(ExceptionCatchingInputStream.java:85)
09-10 09:50:35.082 I/Glide ( 4511): at java.io.FilterInputStream.read(FilterInputStream.java:133)
09-10 09:50:35.082 I/Glide ( 4511): at com.bumptech.glide.util.MarkEnforcingInputStream.read(MarkEnforcingInputStream.java:45)
09-10 09:50:35.082 I/Glide ( 4511): at android.graphics.BitmapFactory.nativeDecodeStream(Native Method)
09-10 09:50:35.082 I/Glide ( 4511): at android.graphics.BitmapFactory.decodeStreamInternal(BitmapFactory.java:646)
09-10 09:50:35.082 I/Glide ( 4511): at android.graphics.BitmapFactory.decodeStream(BitmapFactory.java:622)
09-10 09:50:35.082 I/Glide ( 4511): at com.bumptech.glide.load.resource.bitmap.Downsampler.decodeStream(Downsampler.java:485)
09-10 09:50:35.082 I/Glide ( 4511): at com.bumptech.glide.load.resource.bitmap.Downsampler.decodeFromWrappedStreams(Downsampler.java:276)
09-10 09:50:35.082 I/Glide ( 4511): at com.bumptech.glide.load.resource.bitmap.Downsampler.decode(Downsampler.java:204)
09-10 09:50:35.082 I/Glide ( 4511): at com.bumptech.glide.load.resource.bitmap.StreamBitmapDecoder.decode(StreamBitmapDecoder.java:60)
09-10 09:50:35.082 I/Glide ( 4511): at com.bumptech.glide.load.resource.bitmap.StreamBitmapDecoder.decode(StreamBitmapDecoder.java:17)
09-10 09:50:35.082 I/Glide ( 4511): at com.bumptech.glide.load.resource.bitmap.BitmapDrawableDecoder.decode(BitmapDrawableDecoder.java:45)
09-10 09:50:35.082 I/Glide ( 4511): at com.bumptech.glide.load.engine.DecodePath.decodeResourceWithList(DecodePath.java:67)
09-10 09:50:35.082 I/Glide ( 4511): at com.bumptech.glide.load.engine.DecodePath.decodeResource(DecodePath.java:52)
09-10 09:50:35.082 I/Glide ( 4511): at com.bumptech.glide.load.engine.DecodePath.decode(DecodePath.java:43)
09-10 09:50:35.082 I/Glide ( 4511): at com.bumptech.glide.load.engine.LoadPath.loadWithExceptionList(LoadPath.java:56)
09-10 09:50:35.082 I/Glide ( 4511): at com.bumptech.glide.load.engine.LoadPath.load(LoadPath.java:42)
09-10 09:50:35.082 I/Glide ( 4511): at com.bumptech.glide.load.engine.DecodeJob.runLoadPath(DecodeJob.java:538)
09-10 09:50:35.082 I/Glide ( 4511): at com.bumptech.glide.load.engine.DecodeJob.decodeFromFetcher(DecodeJob.java:510)
09-10 09:50:35.082 I/Glide ( 4511): at com.bumptech.glide.load.engine.DecodeJob.decodeFromData(DecodeJob.java:491)
09-10 09:50:35.082 I/Glide ( 4511): at com.bumptech.glide.load.engine.DecodeJob.decodeFromRetrievedData(DecodeJob.java:445)
09-10 09:50:35.082 I/Glide ( 4511): at com.bumptech.glide.load.engine.DecodeJob.runWrapped(DecodeJob.java:293)
09-10 09:50:35.082 I/Glide ( 4511): at com.bumptech.glide.load.engine.DecodeJob.run(DecodeJob.java:250)
09-10 09:50:35.082 I/Glide ( 4511): at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1133)
09-10 09:50:35.082 I/Glide ( 4511): at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:607)
09-10 09:50:35.082 I/Glide ( 4511): at java.lang.Thread.run(Thread.java:761)
09-10 09:50:35.082 I/Glide ( 4511): at com.bumptech.glide.load.engine.executor.GlideExecutor$DefaultThreadFactory$1.run(GlideExecutor.java:347)
Issue Analytics
- State:
- Created 6 years ago
- Comments:6 (1 by maintainers)
Top Results From Across the Web
java.lang.IllegalStateException: Unbalanced enter/exit #6318
Our usage, which is in a rabbitmq consumer. We use com.squareup.okhttp3:okhttp:3.9.1 and openjdk version "1.8.0_242".
Read more >Unbalanced enter/exit on OkHttp - Stack Overflow
So I have an exception every so often that says java.lang.IllegalStateException: Unbalanced enter/exit and this happens when the onStop of ...
Read more >Android app Crash from exception Java.Lang ... - MSDN
Boolean throwOnFirstException) java.lang.IllegalStateException: Unbalanced enter/exit com.android.okhttp.okio.
Read more >okio/okio/src/main/java/okio/AsyncTimeout.java - Google Git
if (inQueue) throw new IllegalStateException("Unbalanced enter/exit");. long timeoutNanos = timeoutNanos();. boolean hasDeadline = hasDeadline();.
Read more >java.lang.IllegalStateException: Unbalanced enter/exit
Version: 3.9.0. I was investigating a resource leak in Glide which involves lots of parallel requests and adding an try/finally/close in ...
Read more >Top Related Medium Post
No results found
Top Related StackOverflow Question
No results found
Troubleshoot Live Code
Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start FreeTop Related Reddit Thread
No results found
Top Related Hackernoon Post
No results found
Top Related Tweet
No results found
Top Related Dev.to Post
No results found
Top Related Hashnode Post
No results found
Top GitHub Comments
I’m curious about this line:
Could that cause the stream to be consumed by another thread? In that case we’ve got one thread reading while OkHttp’s dispatcher thread is closing.
Yeah sorry this wasn’t clear in my original explanation, the callbacks will post the stream to other threads that will then try to read from them.
Passing closed streams to other threads won’t happen in normal circumstances in Glide, which probably explains why I haven’t seen this more frequently either.