OpenGL Runtime Exception Issue [duplicate] - android

I have android game, using libgdx framework
on Google Play store there are report:
java.lang.RuntimeException: eglSwapBuffers failed: EGL_SUCCESS
at android.opengl.GLSurfaceView$EglHelper.throwEglException(GLSurfaceView.java:1085)
at android.opengl.GLSurfaceView$EglHelper.swap(GLSurfaceView.java:1043)
at android.opengl.GLSurfaceView$GLThread.guardedRun(GLSurfaceView.java:1369)
at android.opengl.GLSurfaceView$GLThread.run(GLSurfaceView.java:1123)
what I can do?
devices reported : Samsung GT-S5830i, Samsung galaxy Y, LGE LG-P990 , Motorola Photon 4G, Motorola Droid X2,

This problem has been reported here before. There is already an issue filed.
You can help by providing more details to this issue.

I made some research and found out that this problem occurs in low end devices because they have low memory. Loading and unloading of textures between two scene crashes SwapBuffer and hence throws this Runtime exception.
Most annoying thing about this issue is that, when I tested in such devices, I didn't get any such error but in playstore I got too many report with this issue.
So, we can tackle this issue in two ways:
1)Filter out low end devices from compatible list.
2)Catch the exception using UncaughtExceptionHandler() and tell user about low memory problem.

Solution in last edit.
It actually did happen on my low end devices as well (GT-S5830 and GT-S5830i).
The thing is, it did not happen because of low memory; I logged the current memory usage of my game and it did not cross 3 megabytes, when I had like 80 or more megabytes of free ram. I even ran System.gc() consistently, which hints the garbage collector to free up some ram space.
I have no workaround but will update this answer as soon as I find one.
After some search, gpu related stuff (like textures) are not managed by the garbage collector (that's why they should be disposed manually). So calling System.gc() is somehow pointless. Still, I'm disposing all of my textures, and the memory usage of my game is pretty low.
I tried all sorts of solutions and nothing worked BUT here is something that should fix the problem (haven't tried this one, but should work nonetheless):
Simply don't load so much textures over and over. My game used to dispose and then initialize all textures whenever the user navigated away from a screen. That is possibly causing the problem. What you need to do is to keep the loaded textures/texture atlases in memory (don't lose their reference). That way, navigating back to a screen wouldn't reload all the textures.
Avoid using raw Textures and instead use a POT (Power Of Two) TextureAtlas.
I will apply these two steps to my project, and if the problem goes away, I'll come back to confirm my solution.
That wasn't the problem at all. I ran a really long loop of disposing and loading of textures, no exception/error was thrown. My above suggestion is not the solution. The problem is probably related to excessive Screen switching, but I guess not since this problem also happens when changing the screen orientation repeatedly from portrait mode to landscape mode and vice versa.
Solution:
I thought that Game's setScreen(screen) calls Screen's dispose() automatically (which is not the case). dispose() was used to dispose all of my underlying textures. I simply solved the problem by calling dispose() in Screen's hide() overridden method.
Using TextureAtlass is very important because you reduce the amount of handles that are attached to each Texture. (Which may be the reason of the EGL_SUCCESS error)
Tested on both GT-S5830 and GT-S5830i (Samsung Galaxy Ace and Samsung Galaxy Y). Problem no longer occurs.

Related

Android admob example interstitial memory leak

I am actually experiencing a heap problem while using interstitials (2.3 Nexus One).
I am able to reproduce the problem using the admob sample from Google play (android sdk). I have just set my ad id and my device id as a test device (I also have the problem without doing setting the test device id).
Just launch the sample, choose interstitial, Load, Display, Close.
Now in DDMS you can see a given amount of Allocated memory after having triggered the GC. (in my case 3.421 MB)
Then if I keep on repeating the Load, Display, Close operation, I see that the Allocated size on the heap just keeps on increasing. After some launches I reach 3.936 MB, and it never seems to stop.
I DO NOT change the phone orientation in between or do anything fancy.
I have tried changing new InterstitialAd(this) to new InterstitialAd(getApplicationContext()) as suggested in some other questions, but it does not change the problem.
On a 4.4.2 emulator the problem seems to exist too (I say seem because as the emulator is really slow it is hard to perform the operation a big number of times).
Of course I have the same problem with my real application. In my real app I also tried recreating the interstital before each loading (after having removed its listener) but the problem is exactly the same, so my guess is that it is not the interstitial instance itself that leaks, but perhaps the web view, or one of admob threads.
In my real application this causes a crash when loading a "big" bitmap (a 800*560 png) because of a OutOfMemoryError failed to allocate... so I am afraid that this may also leak some native memory (which is used for bitmap allocation in 2.3)
EDIT : It seems to leak some native memory indeed, but a very samll quantity.

java.lang.RuntimeException: eglSwapBuffers failed: EGL_SUCCESS report

I have android game, using libgdx framework
on Google Play store there are report:
java.lang.RuntimeException: eglSwapBuffers failed: EGL_SUCCESS
at android.opengl.GLSurfaceView$EglHelper.throwEglException(GLSurfaceView.java:1085)
at android.opengl.GLSurfaceView$EglHelper.swap(GLSurfaceView.java:1043)
at android.opengl.GLSurfaceView$GLThread.guardedRun(GLSurfaceView.java:1369)
at android.opengl.GLSurfaceView$GLThread.run(GLSurfaceView.java:1123)
what I can do?
devices reported : Samsung GT-S5830i, Samsung galaxy Y, LGE LG-P990 , Motorola Photon 4G, Motorola Droid X2,
This problem has been reported here before. There is already an issue filed.
You can help by providing more details to this issue.
I made some research and found out that this problem occurs in low end devices because they have low memory. Loading and unloading of textures between two scene crashes SwapBuffer and hence throws this Runtime exception.
Most annoying thing about this issue is that, when I tested in such devices, I didn't get any such error but in playstore I got too many report with this issue.
So, we can tackle this issue in two ways:
1)Filter out low end devices from compatible list.
2)Catch the exception using UncaughtExceptionHandler() and tell user about low memory problem.
Solution in last edit.
It actually did happen on my low end devices as well (GT-S5830 and GT-S5830i).
The thing is, it did not happen because of low memory; I logged the current memory usage of my game and it did not cross 3 megabytes, when I had like 80 or more megabytes of free ram. I even ran System.gc() consistently, which hints the garbage collector to free up some ram space.
I have no workaround but will update this answer as soon as I find one.
After some search, gpu related stuff (like textures) are not managed by the garbage collector (that's why they should be disposed manually). So calling System.gc() is somehow pointless. Still, I'm disposing all of my textures, and the memory usage of my game is pretty low.
I tried all sorts of solutions and nothing worked BUT here is something that should fix the problem (haven't tried this one, but should work nonetheless):
Simply don't load so much textures over and over. My game used to dispose and then initialize all textures whenever the user navigated away from a screen. That is possibly causing the problem. What you need to do is to keep the loaded textures/texture atlases in memory (don't lose their reference). That way, navigating back to a screen wouldn't reload all the textures.
Avoid using raw Textures and instead use a POT (Power Of Two) TextureAtlas.
I will apply these two steps to my project, and if the problem goes away, I'll come back to confirm my solution.
That wasn't the problem at all. I ran a really long loop of disposing and loading of textures, no exception/error was thrown. My above suggestion is not the solution. The problem is probably related to excessive Screen switching, but I guess not since this problem also happens when changing the screen orientation repeatedly from portrait mode to landscape mode and vice versa.
Solution:
I thought that Game's setScreen(screen) calls Screen's dispose() automatically (which is not the case). dispose() was used to dispose all of my underlying textures. I simply solved the problem by calling dispose() in Screen's hide() overridden method.
Using TextureAtlass is very important because you reduce the amount of handles that are attached to each Texture. (Which may be the reason of the EGL_SUCCESS error)
Tested on both GT-S5830 and GT-S5830i (Samsung Galaxy Ace and Samsung Galaxy Y). Problem no longer occurs.

Open GL stutter when rendering on Galaxy S2

Our Android game has an issue which appears unique to the Galaxy S2.
Occasionally the render will stutter. By this I mean it basically seems to render the last two frames (as though its swapping the last two render buffers without updating either).
What's really odd about this is that the game continues to update, so say the stutter lasts for 2 seconds, the game will have progressed 2 seconds behind the scenes.
This is odd because our code is basically like this:
function Update()
DoGameLogic()
DoRender()
So this means that if our the game has updated, the game has also rendered. The maximum delta time is capped to 1 frame so there must have been more than one Update and thus multiple renders during the stutter.
My current theory is that on most devices the game lags during render, but on the S2 the render calls are executed but they "fall through" without updating the render buffer.
Has anyone run into this problem? I would really appreciate any suggestions about what this could be.
We found out what the problem is.
The Galaxy S 2 was for some reason running out of GL memory. This wasn't apparent on the devices we were testing with, but on other devices it would crash on some Open GL call - not the offending call mind you.
Eventually we tracked it down to using Point sprite VBO's. As the S 2 is a powerful device, we replaced Point sprites with Quad's mimicking point sprites as a workaround.
Incidentally, SoundPool would also run out of memory on this device, requiring another workaround.

lockCanvas() really slow

Testing my game on a slower device (Orange San Francisco aka ZTE Blade) and I have been getting an appalling frame rate.
I put some debug code into the draw loop and discovered the following line is taking over 100ms:
c = mSurfaceHolder.lockCanvas();
Anyone else seen this behaviour? I temporarily replaced the surfaceview by extending View and implementing onDraw(), and I got a much better framerate.
Although in general surfaceView is much faster on my HTC Desire. I am suspicious this may be a Android 2.1 problem. I'm contemplating rooting the phone and upgrading it to 2.2 if possible, but I did want a device running on 2.1 so that might be counter-productive in the long run.
** update **
I've been working on this some more, and have discovered some more puzzling aspects to it.
I rooted the phone and installed 2.2 and the problem still happens. When the app is first started, the lockCanvas is working as expected (0-1 ms). Then at some point during my initialisation, lockCanvas suddenly starts taking approx 100ms.
It might be worth pointing out that I am loading my assets in an Async task, so that I can display a loading screen.
Despite my best efforts to pin down what the program is actually doing when the slowness occurrs I was not able to do so. In fact when I run it in debug mode and single step, it works fast!
Now I discovered that if I add a delay in the constructor of my SurfaceView (of about 10 seconds), the slowness doesn't occur and all works fine.
However if you press Home, and then switch back, the slowness comes back.
I'm pretty much at the end of my tether on this stupid illogical problem! I've got a mind to put it down to a device specific problem.
I feel it could have something to do with memory usage. Maybe something is being swapped out and it affects the video ram?
I'd be interested in theories at least.
About lockCanvas() from docs:
If you call this repeatedly when the
Surface is not ready (before
Callback.surfaceCreated or after
Callback.surfaceDestroyed), your calls
will be throttled to a slow rate in
order to avoid consuming CPU.
Is it possible that your draw loop is initiated too early for some devices? I think this is the problem, since you wrote:
Now I discovered that if I add a delay
in the constructor of my SurfaceView
(of about 10 seconds), the slowness
doesn't occur and all works fine.
So, maybe we could use holder.isCreating() to check state?
this method will return true if canvas still creating.
Something like
while(holder.isCreating()) {}
can=holder.lockCanvas();
But I'm a bit confuse now. As i know colbeck is called when a surfaceview is creates. We should implement SurfaceHolder.Callback interface. And when surface is created callback method
public void surfaceCreated(SurfaceHolder holder) { } will be called.
From surfaceCreated method I'm starting gameloop thread.
I have recently discovered that if large bitmaps are used to draw on the canvas and these bitmaps are stored in the activity class - the "_surfaceHolder.lockCanvas()" command itself takes very long (about 70ms depending on device). HOWEVER, moving these bitmaps storage to other class (in different file, say MY_DATA), and the activity has just a reference to that new class - solves the problem.
I'm have no explanation to this phenomenon.
I was encountered the same mysterious problem with Canvas drawing, but solved it by changing Canvas drawing to drawing on the SurfaceView. But now I have constantly slow lockCanvas() call.
Here is my observation results.
Problem is only present on some devices:
Galaxy Note 3 n900: has problems
Galaxy Note 3 n9005: has problems
Galaxy S4 i9505: has problems
Galaxy Gio: no problems
LG G2 D802: has problems
Galaxy S2 i9100: no problems
I temporarily replaced the surfaceview by extending View and implementing onDraw(), and I got a much better framerate
I also noticed, that Samsung phones using GLES20Canvas instead of regular Canvas with onDraw() drawing, as a result, better performance.

Nexus One / Android "CPU may be pegged" bug

I'm writing a graphically intense game for the Nexus One, using the NDK (revision 4) and OpenGL ES 2.0. We're really pushing the hardware here, and for the most part it works well, except every once in a while I get a serious crash with this log message:
W/SharedBufferStack( 398): waitForCondition(LockCondition) timed out
(identity=9, status=0). CPU may be pegged. trying again.
The entire system locks up, repeats this message over and over, and will either restart after a couple minutes or we have to reboot it manually. We're using Android OS 2.1, update 1.
I know a few other people out there have seen this bug, sometimes in relation to audio. In my case it's caused by the SharedBufferStack, so I'm guessing it's an OpenGL issue. Has anyone encountered this, and better yet fixed it? Or does anyone know what's going on with the SharedBufferStack to help me narrow things down?
I don't believe such error can occur in audio code, SharedBufferStack is only used in Surface libraries. Most probably this is a bug in EGL swapBuffers or SurfaceFlinger implementation, and you should file it to the bug tracker.
I got CPU may be pegged messages on LogCat because I had a ArrayBlockingQueue in my code. If you have any blocking queue (as seems to be the case with audio buffers), be sure to BlockingQueue.put() only if you have timing control enough to properly BlockingQueue.take() elements to make room for it. Or else, have a look on using BlockingQueue.offer().
The waitForCondition() causes the lockup (system-freeze).
But it is not the root-cause. This seems to be a issue with
The audio-framework (ur game has sounds?)
-or-
The GL rendering-subsystem.
Any "CPU-pegged" messages in the log?
You might want to take a look at this:
http://soledadpenades.com/2009/08/25/is-the-cpu-pegged-and-friends/
There seems to be a driver problem with eglSwapBuffers():
http://code.google.com/p/android/issues/detail?id=20833&q=cpu%20may%20be%20pegged&colspec=ID%20Type%20Status%20Owner%20Summary%20Stars
One workaround is to call glFinish() preceding your call to eglSwapBuffers(), however this will induce a performance hit.
FWIW, I hit this issue recently while developing on Android 2.3.4 using GL ES 2 on a Samsung Galaxy S.
The issue for me was a bug in my glDrawArrays call - I was rendering past the end of the buffer, i.e. the "count" I was passing in was greater than the actual count. Interestingly, that call did not throw an exception, but it would intermittently result in the issue you described. Also, the buffer I ended up rendering looked wrong so I knew something was off. The "CPU may be pegged" thing just made it more annoying to track down the real issue.

Categories

Resources