Monkey runtime error: (Heap Size...

Monkey Targets Forums/Android/Monkey runtime error: (Heap Size...

siread(Posted 2012) [#1]
I have had a lot of complaints about crashes on HTC Wildfire devices, so I managed to get hold of one for testing. It seems that the game is runs fine for a few minutes then crashes out with the following error:

Monkey runtime error: (Heap Size=19143KB, Allocated=11107KB, Bitmap Size=0KB)

It can occur seemingly at random. The Heap and Allocated sizes vary but the Bitmap Size is always zero. The phone specs are similar to my other Android (512mb ram) which runs the game fine. Any clues what this means or why it is happening?


therevills(Posted 2012) [#2]
Is the plain old HTC Wildfire?

http://www.gsmarena.com/results.php3?sQuickSearch=yes&sName=HTC+Wildfire

If so, these devices are very slow and low res, maybe it is not fast enough to clean up the memory before running out.

Looking here: http://www.gsmarena.com/htc_wildfire-3337.php the device only has 384 MB RAM, the 512MB is ROM...


muddy_shoes(Posted 2012) [#3]
If you have the device can you post the full log from the debug connection? It looks like a normal Out Of Memory error and the log should give some clues as to where it's occurring.


Xaron(Posted 2012) [#4]
I had that problem ages ago with an older Monkey version and on some devices. It ran fairly well on my Desire HD but had exactly these out of memory errors on some lower spec devices.

Well that was the thread: http://www.monkeycoder.co.nz/Community/posts.php?topic=951

Mark did a bugfix as well some time ago:
http://www.monkeycoder.co.nz/Community/posts.php?topic=1894

For me it helped to use Discard() a lot to remove images from memory I don't use at the moment...


siread(Posted 2012) [#5]
Sorry, the phone I am testing with is a Wildfire S, although I've had complaints from users with both devices.

Noob question: How do a get a debug log from an Android device?

I didn't know about Discard(). How does it differ from simply setting "img = Null"?


skid(Posted 2012) [#6]
I would test with lores graphics and maybe 16 bit mode for devices where you are most likely running out of texture resources.


muddy_shoes(Posted 2012) [#7]
This is a reasonable place to start concerning debug connections: http://developer.android.com/guide/developing/debugging/debugging-projects.html

If you're going to be developing on Android then it's definitely worth getting Eclipse and DDMS set up.


TeaBoy(Posted 2012) [#8]
Hi Siread,

I had a problem like this ages ago with my standard Wildfire, I had to change the heap size to 512, from 1024 to get it working properly.

Go to the android SDK folder and look up platform-tools, edit dx.bat

you should see this abit further down:

REM By default, give dx a max heap size of 1 gig and a stack size of 1meg.
rem This can be overridden by using "-JXmx..." and "-JXss..." options below.
set defaultXmx=-Xmx512M <- change to this.
set defaultXss=-Xss1m

it may work for you, but I have no problems working with monkey.


siread(Posted 2012) [#9]
Hoh yeah! Worked a treat, thanks TeaBoy.


siread(Posted 2012) [#10]
Damn, I spoke too soon. It worked flawlessly until I pressed the home button, then when switched back to the game the same error appeared immediately. Then every time I start the game (after forcing it to stop) I get the error quite soon.

It seems that restarting the device allows the game to run along perfectly until you switch out of it and go back or reload.


Xaron(Posted 2012) [#11]
Yes, that's why I use Discard() a lot. Looks like "img = 0" doesn't work the same way...


siread(Posted 2012) [#12]
I've been trying to Discard() as much as possible, but still getting the error. So I finally got around to installing Eclipse... After pressing the Home button and returning to the game the heap crash occurred. This is the log:

03-30 15:40:07.441: D/dalvikvm(8837): GC_CONCURRENT freed 1811K, 52% free 8508K/17671K, external 0K/0K, paused 6ms+24ms
03-30 15:42:43.991: D/dalvikvm(8837): GC_CONCURRENT freed 1812K, 52% free 8506K/17671K, external 0K/0K, paused 7ms+22ms
03-30 15:45:19.481: D/dalvikvm(8837): GC_CONCURRENT freed 1811K, 52% free 8502K/17671K, external 0K/0K, paused 6ms+23ms
03-30 15:47:55.131: D/dalvikvm(8837): GC_CONCURRENT freed 1807K, 52% free 8501K/17671K, external 0K/0K, paused 5ms+22ms
03-30 15:50:31.751: D/dalvikvm(8837): GC_CONCURRENT freed 1808K, 52% free 8500K/17671K, external 0K/0K, paused 6ms+8ms
03-30 15:53:07.831: D/dalvikvm(8837): GC_CONCURRENT freed 1798K, 52% free 8510K/17671K, external 0K/0K, paused 7ms+21ms
03-30 15:55:43.991: D/dalvikvm(8837): GC_CONCURRENT freed 1812K, 52% free 8508K/17671K, external 0K/0K, paused 8ms+22ms
03-30 15:56:23.571: V/SoundPool-JNI(8837): android_media_SoundPool_pause
03-30 15:56:23.571: V/SoundPool(8837): pause(15)
03-30 15:56:23.571: V/SoundPool-JNI(8837): android_media_SoundPool_pause
03-30 15:56:23.571: V/SoundPool(8837): pause(11)
03-30 15:56:23.571: V/SoundPool-JNI(8837): android_media_SoundPool_pause
03-30 15:56:23.571: V/SoundPool(8837): pause(12)
03-30 15:56:56.541: D/dalvikvm(8837): GC_EXPLICIT freed 447K, 52% free 8499K/17671K, external 0K/0K, paused 123ms
03-30 16:01:55.291: V/SoundPool-JNI(8837): android_media_SoundPool_resume
03-30 16:01:55.291: V/SoundPool(8837): resume(15)
03-30 16:01:55.291: V/SoundPool-JNI(8837): android_media_SoundPool_resume
03-30 16:01:55.291: V/SoundPool(8837): resume(11)
03-30 16:01:55.291: V/SoundPool-JNI(8837): android_media_SoundPool_resume
03-30 16:01:55.291: V/SoundPool(8837): resume(12)
03-30 16:02:15.531: D/dalvikvm(8837): GC_FOR_MALLOC freed 1148K, 52% free 8591K/17671K, external 0K/0K, paused 84ms
03-30 16:02:15.661: I/dalvikvm-heap(8837): Forcing collection of SoftReferences for 4194320-byte allocation
03-30 16:02:15.751: D/dalvikvm(8837): GC_FOR_MALLOC freed 14K, 52% free 8576K/17671K, external 0K/0K, paused 86ms
03-30 16:02:15.881: E/dalvikvm-heap(8837): Out of memory on a 4194320-byte allocation.
03-30 16:02:15.881: I/dalvikvm(8837): "GLThread 13" prio=5 tid=12 RUNNABLE
03-30 16:02:15.881: I/dalvikvm(8837):   | group="main" sCount=0 dsCount=0 obj=0x40582e00 self=0x23abe8
03-30 16:02:15.881: I/dalvikvm(8837):   | sysTid=8850 nice=0 sched=0/0 cgrp=default handle=2338080
03-30 16:02:15.881: I/dalvikvm(8837):   | schedstat=( 5977828495494 1078098475910 2138280 )
03-30 16:02:15.881: I/dalvikvm(8837):   at com.newstargames.newstarsoccer.gxtkSurface.Bind(MonkeyGame.java:~1535)
03-30 16:02:15.881: I/dalvikvm(8837):   at com.newstargames.newstarsoccer.gxtkGraphics.Flush(MonkeyGame.java:1094)
03-30 16:02:15.881: I/dalvikvm(8837):   at com.newstargames.newstarsoccer.gxtkGraphics.SetScissor(MonkeyGame.java:1203)
03-30 16:02:15.881: I/dalvikvm(8837):   at com.newstargames.newstarsoccer.bb_graphics.bb_graphics_SetScissor(MonkeyGame.java:51110)
03-30 16:02:15.881: I/dalvikvm(8837):   at com.newstargames.newstarsoccer.bb_autofit_VirtualDisplay.m_SetVScissor(MonkeyGame.java:6471)
03-30 16:02:15.881: I/dalvikvm(8837):   at com.newstargames.newstarsoccer.bb_sigui_TLabel.m_Draw(MonkeyGame.java:11561)
03-30 16:02:15.881: I/dalvikvm(8837):   at com.newstargames.newstarsoccer.bb_sigui_TScreen.m_Draw(MonkeyGame.java:7622)
03-30 16:02:15.881: I/dalvikvm(8837):   at com.newstargames.newstarsoccer.bb_sigui_TScreen.g_Render(MonkeyGame.java:7701)
03-30 16:02:15.881: I/dalvikvm(8837):   at com.newstargames.newstarsoccer.bb__GameEngine.m_OnRender(MonkeyGame.java:2622)
03-30 16:02:15.881: I/dalvikvm(8837):   at com.newstargames.newstarsoccer.bb_app_AppDevice.OnRender(MonkeyGame.java:2710)
03-30 16:02:15.881: I/dalvikvm(8837):   at com.newstargames.newstarsoccer.gxtkApp.InvokeOnRender(MonkeyGame.java:882)
03-30 16:02:15.881: I/dalvikvm(8837):   at com.newstargames.newstarsoccer.gxtkApp.onDrawFrame(MonkeyGame.java:808)
03-30 16:02:15.891: I/dalvikvm(8837):   at android.opengl.GLSurfaceView$GLThread.guardedRun(GLSurfaceView.java:1363)
03-30 16:02:15.891: I/dalvikvm(8837):   at android.opengl.GLSurfaceView$GLThread.run(GLSurfaceView.java:1118)
03-30 16:02:15.901: E/dalvikvm(8837): Out of memory: Heap Size=17671KB, Allocated=8576KB, Bitmap Size=0KB, Limit=20480KB
03-30 16:02:15.911: E/dalvikvm(8837): Extra info: Footprint=17671KB, Allowed Footprint=17671KB, Trimmed=5328KB
03-30 16:02:15.961: V/SoundPool-JNI(8837): android_media_SoundPool_stop
03-30 16:02:15.961: V/SoundPool(8837): stop(15)
03-30 16:02:15.961: V/SoundPool(8837): done(15)
03-30 16:02:15.961: V/SoundPool(8837): move to front
03-30 16:02:15.961: V/SoundPool-JNI(8837): android_media_SoundPool_stop
03-30 16:02:15.961: V/SoundPool(8837): stop(11)
03-30 16:02:15.961: V/SoundPool(8837): done(11)
03-30 16:02:15.961: V/SoundPool(8837): move to front
03-30 16:02:15.961: V/SoundPool-JNI(8837): android_media_SoundPool_stop
03-30 16:02:15.961: V/SoundPool(8837): stop(12)
03-30 16:02:15.961: V/SoundPool-JNI(8837): android_media_SoundPool_stop
03-30 16:02:15.961: V/SoundPool(8837): stop(9)
03-30 16:02:15.961: V/SoundPool(8837): done(9)
03-30 16:02:15.961: V/SoundPool(8837): move to front
03-30 16:02:15.961: V/SoundPool-JNI(8837): android_media_SoundPool_stop
03-30 16:02:15.961: V/SoundPool(8837): stop(10)
03-30 16:02:15.961: V/SoundPool-JNI(8837): android_media_SoundPool_release
03-30 16:02:15.961: V/SoundPool(8837): SoundPool destructor
03-30 16:02:15.961: V/SoundPoolThread(8837): Got message m=1, mData=0
03-30 16:02:15.961: V/SoundPoolThread(8837): goodbye
03-30 16:02:15.961: V/SoundPoolThread(8837): return from quit
03-30 16:02:15.961: V/SoundPool(8837): awake
03-30 16:02:15.961: V/SoundPool(8837): goodbye
03-30 16:02:15.961: V/SoundPool(8837): return from quit
03-30 16:02:15.961: V/SoundPool(8837): SoundChannel destructor
03-30 16:02:15.961: V/SoundPool(8837): SoundChannel destructor
03-30 16:02:15.961: V/SoundPool(8837): SoundChannel destructor
03-30 16:02:15.961: V/SoundPool(8837): SoundChannel destructor
03-30 16:02:15.961: V/SoundPool(8837): SoundChannel destructor
03-30 16:02:15.961: V/SoundPool(8837): SoundChannel destructor
03-30 16:02:15.961: V/SoundPool(8837): SoundChannel destructor
03-30 16:02:15.961: V/SoundPool(8837): SoundChannel destructor
03-30 16:02:15.961: V/SoundPool(8837): SoundChannel destructor
03-30 16:02:15.961: V/SoundPool(8837): SoundChannel destructor
03-30 16:02:15.971: V/SoundPool(8837): SoundChannel destructor
03-30 16:02:15.971: V/SoundPool(8837): SoundChannel destructor
03-30 16:02:15.971: V/SoundPool(8837): SoundChannel destructor
03-30 16:02:15.971: V/SoundPool(8837): SoundChannel destructor
03-30 16:02:15.971: V/SoundPool(8837): SoundChannel destructor
03-30 16:02:15.971: V/SoundPool(8837): SoundChannel destructor
03-30 16:02:15.971: V/SoundPool(8837): SoundChannel destructor
03-30 16:02:15.971: V/SoundPool(8837): SoundChannel destructor
03-30 16:02:15.971: V/SoundPool(8837): SoundChannel destructor
03-30 16:02:15.971: V/SoundPool(8837): SoundChannel destructor
03-30 16:02:15.971: V/SoundPool(8837): SoundChannel destructor
03-30 16:02:15.971: V/SoundPool(8837): SoundChannel destructor
03-30 16:02:15.971: V/SoundPool(8837): SoundChannel destructor
03-30 16:02:15.971: V/SoundPool(8837): SoundChannel destructor
03-30 16:02:15.971: V/SoundPool(8837): SoundChannel destructor
03-30 16:02:15.971: V/SoundPool(8837): SoundChannel destructor
03-30 16:02:15.971: V/SoundPool(8837): SoundChannel destructor
03-30 16:02:15.971: V/SoundPool(8837): SoundChannel destructor
03-30 16:02:15.971: V/SoundPool(8837): SoundChannel destructor
03-30 16:02:15.971: V/SoundPool(8837): SoundChannel destructor
03-30 16:02:15.971: V/SoundPool(8837): stop track
03-30 16:02:15.971: V/SoundPool(8837): SoundChannel destructor
03-30 16:02:15.971: V/SoundPool(8837): stop track
03-30 16:02:15.971: V/SoundPool(8837): SoundChannel destructor
03-30 16:02:15.971: V/SoundPool(8837): stop track
03-30 16:02:15.971: V/SoundPool(8837): clear samples
03-30 16:02:15.971: V/SoundPool(8837): Sample::destructor sampleID=1, fd=-1
03-30 16:02:15.981: V/SoundPool(8837): Sample::destructor sampleID=2, fd=-1
03-30 16:02:15.981: V/SoundPool(8837): Sample::destructor sampleID=3, fd=-1
03-30 16:02:15.981: V/SoundPool(8837): Sample::destructor sampleID=4, fd=-1
03-30 16:02:15.981: V/SoundPool(8837): Sample::destructor sampleID=5, fd=-1
03-30 16:02:15.981: V/SoundPool(8837): Sample::destructor sampleID=6, fd=-1
03-30 16:02:15.981: V/SoundPool(8837): Sample::destructor sampleID=7, fd=-1
03-30 16:02:15.981: V/SoundPool(8837): Sample::destructor sampleID=8, fd=-1
03-30 16:02:15.981: V/SoundPool(8837): Sample::destructor sampleID=10, fd=-1
03-30 16:02:15.981: V/SoundPool(8837): Sample::destructor sampleID=11, fd=-1
03-30 16:02:15.981: V/SoundPool(8837): Sample::destructor sampleID=12, fd=-1
03-30 16:02:15.981: V/SoundPool(8837): Sample::destructor sampleID=13, fd=-1
03-30 16:02:15.991: V/SoundPool(8837): Sample::destructor sampleID=23, fd=-1
03-30 16:02:15.991: V/SoundPoolThread(8837): return from quit
03-30 16:02:16.021: I/[Monkey](8837): Java exception:java.lang.OutOfMemoryError: (Heap Size=17671KB, Allocated=8576KB, Bitmap Size=0KB)



JIM(Posted 2012) [#13]
Any way you could get away with smaller resolution graphics?
Wonder if there's any way to get monkey to work with any texture compression (ETC for starters).

Unless you're allocating inhuman amounts of data for gameplay, the only way you can lower the memory is from data (lower quality graphics, lower quality sounds, etc.).


muddy_shoes(Posted 2012) [#14]
03-30 16:02:15.881: E/dalvikvm-heap(8837): Out of memory on a 4194320-byte allocation.

Are you using a 1024x1024 atlas?


therevills(Posted 2012) [#15]
Out of memory on a 4194320-byte allocation.

Are you using a 1024x1024 atlas?


Wouldnt that be 1024*1024*4 = 4194304? Whats the other 16 bytes?


muddy_shoes(Posted 2012) [#16]
Header of some sort.


siread(Posted 2012) [#17]
With regards to lowering the quality/res, the game already does that quite a bit. Low-res devices load up half-scale images, and the sounds files are very small oggs. Actually, the only images that aren't loaded half-scale are the fonts, and they are the only atlas' I use. There are 2 of them at 1024x1024 and 1 at 512x1024.


muddy_shoes(Posted 2012) [#18]
At first glance then I'd guess that this is something to do with heap fragmentation. However, I've read that Android does some odd things behind the scenes with allocating memory both on the VM heap or on the native heap depending on the operation involved.

You say that all these atlases are just the fonts? So your other images are loaded up individually? Do you load your font atlases first, last or just whenever? Are they all loaded and references held while the game is running? Are you actively discarding them at some point?

I'll see if I can look at the heap behaviour on my own phone at some point if there's a free version of NSS.


AdamRedwoods(Posted 2012) [#19]

At first glance then I'd guess that this is something to do with heap fragmentation.


http://stackoverflow.com/questions/6349943/android-bitmaps-recycling-and-heap-fragmentation


muddy_shoes(Posted 2012) [#20]
A quick look in the Bind() call for Android shows that it gets a full copy of the pixel data from the bitmap and then allocates ByteBuffers for manipulating that pixel data into different formats. I'm sure those will be on the VM heap, so fragmentation seems more and more likely to be the culprit.


slenkar(Posted 2012) [#21]
So the solution is to use seperate images?


muddy_shoes(Posted 2012) [#22]
@siread: If you're using RGBA8888 images (probably, you are) then maybe you could try replacing that section of Bind in mojo.android.java with this as a test (i.e. don't go throwing out a release using this even if it works as the IntBuffer method may well have issues with endian-ness on different phones):



It should reduce the memory allocation of that operation by about half. It's also a lot faster. It doesn't resolve heap fragmentation entirely, but it may well avoid the failed allocation.

@slenkar: Loading every image separately would make it far less likely for fragmentation to cause an allocation failure, yes. It's not really a good solution considering the general advantages of using image atlases though.

Fixing heap fragmentation usually means ensuring that your allocations and releases are done in a systematic manner so that you don't end up poking "holes" in the available memory.


muddy_shoes(Posted 2012) [#23]
In fact, you can just replace everything in Bind() after "vscale=1.0f/(float)texheight;" with this and it seems all fine and much faster than what's there now (like 40ms versus 2.5s to bind a 1024x1024 bitmap):




AdamRedwoods(Posted 2012) [#24]
That for-next loop is doing a pre-multiplied alpha, fyi.


muddy_shoes(Posted 2012) [#25]
Sure. GLUtils appears to create a pre-multiplied alpha texture.


siread(Posted 2012) [#26]
Ok, so that made a massive improvement on the Wildfire S! (Only tested on the Wildfire so far, but I have 2 other phones to try.) Images load noticeably faster and I could press the home button and return to the game multiple times without an issue.

That is until I tried to load the game save file. The first load is fine, but quitting your game then attempting to load it again (without switching out of the app at all) causes the same problem as before. The save state is around 180k and is loaded during OnCreate and remains in memory throughout...

		' Load save state
		Local str:String = LoadState()
		
		If str <> ""
			' The save state string is converted into an array. The first field holds global data 
			' such as the arcade highscore whilst the following fields store career data.
			loadstring = str.Split(";")
			TPlayer.LoadGlobalData(GameEngine.loadstring[0])
		End


Then when the player clicks 'Load Career' a new player object is created and the fields are populated from the loadstring...
		player = New TPlayer
		
		' Player data
		Local playerdata:String[] = GameEngine.loadstring[1].Split(",")
		Local count:Int = 0
		
		player.date = TMyDate.Create(Int(playerdata[count])); count+=1
		player.clubnationid = Int(playerdata[count]); count+=1

etc.


Different parts of the loadstring array contain the data for match results, competition data and so on. I guess I now need to determine exactly where the crash is occurring during the populating of the player/competition fields...


siread(Posted 2012) [#27]
Ah, of course. It's nothing to do with the save file but the loading of the club data file which is 888kb. (It loads the whole file but only stores details of the clubs that are actually required in your league, so just a small percentage of the main file.)

I should be able to vastly reduce the size of this file because it contains a lot of unnecessary data for the mobile version of NSS (alternative kit colours, stadium names, nick-names and so on...)


siread(Posted 2012) [#28]
Hot damn, it seems to work. I can switch out of the app and back, load up the save file multiple times... I'm sure it's not flawless (and there are often issues with some of the wrong images being used after pressing the Home button - what the hell is that all about?) but this is a massive improvement.

muddy_shoes, since we're not using the IntBuffer thing, does that mean there shouldn't be an endian problem on different devices? (Big thanks for your help, btw.) :)


muddy_shoes(Posted 2012) [#29]
Android compatibility is a weird beast. In theory, seeing as GLUtils is an Android library, that version should be as compatible across devices as you can get. In practice? I can't guarantee anything as I've got a test device collection of one phone. It might be worth asking Mark Sibly if he tried it and discarded it as an option for a reason.

Did you grab a log of the loading OOM failure? I'm wondering if there are similar memory expensive operations there that could be improved.

That wrong images thing is curious. Is that pre-existing or since you changed to the GLUtils texture loader?


siread(Posted 2012) [#30]
I believe this log occurred during the loading of data:
04-03 17:52:48.215: V/SoundPool(14996): move to front
04-03 17:52:48.305: D/dalvikvm(14996): GC_CONCURRENT freed 2372K, 65% free 7034K/19655K, external 0K/0K, paused 5ms+9ms
04-03 17:52:48.405: D/dalvikvm(14996): GC_FOR_MALLOC freed 459K, 63% free 7447K/19655K, external 0K/0K, paused 68ms
04-03 17:52:48.505: D/dalvikvm(14996): GC_FOR_MALLOC freed 504K, 60% free 7959K/19655K, external 0K/0K, paused 66ms
04-03 17:52:48.845: D/dalvikvm(14996): GC_CONCURRENT freed 383K, 53% free 9326K/19655K, external 0K/0K, paused 5ms+9ms
04-03 17:52:49.215: D/dalvikvm(14996): GC_FOR_MALLOC freed 910K, 52% free 9494K/19655K, external 0K/0K, paused 67ms
04-03 17:52:49.545: D/dalvikvm(14996): GC_FOR_MALLOC freed 646K, 51% free 9818K/19655K, external 0K/0K, paused 67ms
04-03 17:52:50.005: D/dalvikvm(14996): GC_FOR_MALLOC freed 970K, 48% free 10304K/19655K, external 0K/0K, paused 67ms
04-03 17:52:50.005: I/dalvikvm-heap(14996): Forcing collection of SoftReferences for 2235124-byte allocation
04-03 17:52:50.065: D/dalvikvm(14996): GC_FOR_MALLOC freed <1K, 48% free 10303K/19655K, external 0K/0K, paused 69ms
04-03 17:52:50.065: E/dalvikvm-heap(14996): Out of memory on a 2235124-byte allocation.
04-03 17:52:50.075: I/dalvikvm(14996): "GLThread 11" prio=5 tid=11 RUNNABLE
04-03 17:52:50.075: I/dalvikvm(14996):   | group="main" sCount=0 dsCount=0 obj=0x405837e0 self=0x23ee18
04-03 17:52:50.075: I/dalvikvm(14996):   | sysTid=15009 nice=0 sched=0/0 cgrp=default handle=2355024
04-03 17:52:50.075: I/dalvikvm(14996):   | schedstat=( 28913726823 12060485807 19280 )
04-03 17:52:50.075: I/dalvikvm(14996):   at java.lang.AbstractStringBuilder.enlargeBuffer(AbstractStringBuilder.java:~95)
04-03 17:52:50.075: I/dalvikvm(14996):   at java.lang.AbstractStringBuilder.append0(AbstractStringBuilder.java:140)
04-03 17:52:50.075: I/dalvikvm(14996):   at java.lang.StringBuffer.append(StringBuffer.java:126)
04-03 17:52:50.075: I/dalvikvm(14996):   at com.newstargames.newstarsoccer.MonkeyData.loadString(MonkeyGame.java:114)
04-03 17:52:50.075: I/dalvikvm(14996):   at com.newstargames.newstarsoccer.MonkeyData.loadString(MonkeyGame.java:137)
04-03 17:52:50.075: I/dalvikvm(14996):   at com.newstargames.newstarsoccer.gxtkApp.LoadString(MonkeyGame.java:918)
04-03 17:52:50.075: I/dalvikvm(14996):   at com.newstargames.newstarsoccer.bb_app.bb_app_LoadString(MonkeyGame.java:30679)
04-03 17:52:50.075: I/dalvikvm(14996):   at com.newstargames.newstarsoccer.bb_data_club_TClub.g_LoadData(MonkeyGame.java:12246)
04-03 17:52:50.075: I/dalvikvm(14996):   at com.newstargames.newstarsoccer.bb_class_player_TPlayer.g_LoadCareer(MonkeyGame.java:3190)
04-03 17:52:50.075: I/dalvikvm(14996):   at com.newstargames.newstarsoccer.bb_screen_message_TScreen_Message.g_DoCallFunction(MonkeyGame.java:10020)
04-03 17:52:50.075: I/dalvikvm(14996):   at com.newstargames.newstarsoccer.bb_screen_message_TScreen_Message.g_Draw(MonkeyGame.java:10405)
04-03 17:52:50.075: I/dalvikvm(14996):   at com.newstargames.newstarsoccer.bb_sigui.bb_sigui_ScreenDrawExtra(MonkeyGame.java:29128)
04-03 17:52:50.075: I/dalvikvm(14996):   at com.newstargames.newstarsoccer.bb_sigui_TScreen.m_Draw(MonkeyGame.java:5257)
04-03 17:52:50.075: I/dalvikvm(14996):   at com.newstargames.newstarsoccer.bb_sigui_TScreen.g_Render(MonkeyGame.java:5290)
04-03 17:52:50.075: I/dalvikvm(14996):   at com.newstargames.newstarsoccer.bb__GameEngine.m_OnRender(MonkeyGame.java:2390)
04-03 17:52:50.075: I/dalvikvm(14996):   at com.newstargames.newstarsoccer.bb_app_AppDevice.OnRender(MonkeyGame.java:2438)
04-03 17:52:50.075: I/dalvikvm(14996):   at com.newstargames.newstarsoccer.gxtkApp.InvokeOnRender(MonkeyGame.java:882)
04-03 17:52:50.075: I/dalvikvm(14996):   at com.newstargames.newstarsoccer.gxtkApp.onDrawFrame(MonkeyGame.java:808)
04-03 17:52:50.075: I/dalvikvm(14996):   at android.opengl.GLSurfaceView$GLThread.guardedRun(GLSurfaceView.java:1363)
04-03 17:52:50.075: I/dalvikvm(14996):   at android.opengl.GLSurfaceView$GLThread.run(GLSurfaceView.java:1118)
04-03 17:52:50.075: E/dalvikvm(14996): Out of memory: Heap Size=19655KB, Allocated=10303KB, Bitmap Size=0KB, Limit=20480KB
04-03 17:52:50.075: E/dalvikvm(14996): Extra info: Footprint=19655KB, Allowed Footprint=19655KB, Trimmed=7844KB
04-03 17:52:50.075: V/SoundPool-JNI(14996): android_media_SoundPool_stop
04-03 17:52:50.075: V/SoundPool(14996): stop(8)
04-03 17:52:50.075: V/SoundPool(14996): done(8)
04-03 17:52:50.075: V/SoundPool(14996): move to front
04-03 17:52:50.085: V/SoundPool-JNI(14996): android_media_SoundPool_release
04-03 17:52:50.085: V/SoundPool(14996): SoundPool destructor
04-03 17:52:50.085: V/SoundPoolThread(14996): Got message m=1, mData=0
04-03 17:52:50.085: V/SoundPoolThread(14996): goodbye
04-03 17:52:50.085: V/SoundPoolThread(14996): return from quit
04-03 17:52:50.085: V/SoundPool(14996): awake
04-03 17:52:50.085: V/SoundPool(14996): goodbye
04-03 17:52:50.085: V/SoundPool(14996): return from quit
04-03 17:52:50.085: V/SoundPool(14996): SoundChannel destructor
04-03 17:52:50.085: V/SoundPool(14996): SoundChannel destructor
04-03 17:52:50.085: V/SoundPool(14996): SoundChannel destructor
04-03 17:52:50.085: V/SoundPool(14996): SoundChannel destructor
04-03 17:52:50.085: V/SoundPool(14996): SoundChannel destructor
04-03 17:52:50.085: V/SoundPool(14996): SoundChannel destructor
04-03 17:52:50.085: V/SoundPool(14996): SoundChannel destructor
04-03 17:52:50.085: V/SoundPool(14996): SoundChannel destructor
04-03 17:52:50.085: V/SoundPool(14996): SoundChannel destructor
04-03 17:52:50.085: V/SoundPool(14996): SoundChannel destructor
04-03 17:52:50.085: V/SoundPool(14996): SoundChannel destructor
04-03 17:52:50.085: V/SoundPool(14996): SoundChannel destructor
04-03 17:52:50.085: V/SoundPool(14996): SoundChannel destructor
04-03 17:52:50.085: V/SoundPool(14996): SoundChannel destructor
04-03 17:52:50.085: V/SoundPool(14996): SoundChannel destructor
04-03 17:52:50.085: V/SoundPool(14996): SoundChannel destructor
04-03 17:52:50.085: V/SoundPool(14996): SoundChannel destructor
04-03 17:52:50.085: V/SoundPool(14996): SoundChannel destructor
04-03 17:52:50.085: V/SoundPool(14996): SoundChannel destructor
04-03 17:52:50.085: V/SoundPool(14996): SoundChannel destructor
04-03 17:52:50.085: V/SoundPool(14996): SoundChannel destructor
04-03 17:52:50.085: V/SoundPool(14996): SoundChannel destructor
04-03 17:52:50.085: V/SoundPool(14996): SoundChannel destructor
04-03 17:52:50.085: V/SoundPool(14996): SoundChannel destructor
04-03 17:52:50.085: V/SoundPool(14996): SoundChannel destructor
04-03 17:52:50.085: V/SoundPool(14996): SoundChannel destructor
04-03 17:52:50.085: V/SoundPool(14996): SoundChannel destructor
04-03 17:52:50.085: V/SoundPool(14996): SoundChannel destructor
04-03 17:52:50.085: V/SoundPool(14996): SoundChannel destructor
04-03 17:52:50.085: V/SoundPool(14996): SoundChannel destructor
04-03 17:52:50.085: V/SoundPool(14996): SoundChannel destructor
04-03 17:52:50.085: V/SoundPool(14996): SoundChannel destructor
04-03 17:52:50.085: V/SoundPool(14996): stop track
04-03 17:52:50.095: V/SoundPool(14996): clear samples
04-03 17:52:50.095: V/SoundPool(14996): Sample::destructor sampleID=1, fd=-1
04-03 17:52:50.095: V/SoundPool(14996): Sample::destructor sampleID=2, fd=-1
04-03 17:52:50.095: V/SoundPool(14996): Sample::destructor sampleID=3, fd=-1
04-03 17:52:50.095: V/SoundPool(14996): Sample::destructor sampleID=4, fd=-1
04-03 17:52:50.095: V/SoundPool(14996): Sample::destructor sampleID=5, fd=-1
04-03 17:52:50.095: V/SoundPool(14996): Sample::destructor sampleID=6, fd=-1
04-03 17:52:50.095: V/SoundPool(14996): Sample::destructor sampleID=7, fd=-1
04-03 17:52:50.095: V/SoundPool(14996): Sample::destructor sampleID=8, fd=-1
04-03 17:52:50.095: V/SoundPool(14996): Sample::destructor sampleID=12, fd=-1
04-03 17:52:50.095: V/SoundPool(14996): Sample::destructor sampleID=13, fd=-1
04-03 17:52:50.095: V/SoundPool(14996): Sample::destructor sampleID=14, fd=-1
04-03 17:52:50.095: V/SoundPool(14996): Sample::destructor sampleID=15, fd=-1
04-03 17:52:50.095: V/SoundPool(14996): Sample::destructor sampleID=16, fd=-1
04-03 17:52:50.095: V/SoundPool(14996): Sample::destructor sampleID=17, fd=-1
04-03 17:52:50.095: V/SoundPool(14996): Sample::destructor sampleID=18, fd=-1
04-03 17:52:50.095: V/SoundPool(14996): Sample::destructor sampleID=19, fd=-1
04-03 17:52:50.095: V/SoundPool(14996): Sample::destructor sampleID=20, fd=-1
04-03 17:52:50.095: V/SoundPool(14996): Sample::destructor sampleID=21, fd=-1
04-03 17:52:50.095: V/SoundPool(14996): Sample::destructor sampleID=22, fd=-1
04-03 17:52:50.095: V/SoundPool(14996): Sample::destructor sampleID=23, fd=-1
04-03 17:52:50.095: V/SoundPool(14996): Sample::destructor sampleID=24, fd=-1
04-03 17:52:50.095: V/SoundPoolThread(14996): return from quit
04-03 17:52:50.095: I/[Monkey](14996): Java exception:java.lang.OutOfMemoryError: (Heap Size=19655KB, Allocated=10303KB, Bitmap Size=0KB)
04-03 17:52:53.875: W/KeyCharacterMap(14996): Can't open keycharmap file
04-03 17:52:53.875: W/KeyCharacterMap(14996): Error loading keycharmap file '/system/usr/keychars/cy8c-touchscreen.kcm.bin'. hw.keyboards.65537.devname='cy8c-touchscreen'
04-03 17:52:53.875: I/KeyCharacterMap(14996): Using default keymap: /system/usr/keychars/qwerty.kcm.bin
04-03 17:53:06.735: D/dalvikvm(14996): Calling exit(1)


The wrong images thing was happening before. It's basically this issue:


Sometimes though the images aren't blank they are other random images, stretched and distorted. It often happens to the font as well.


muddy_shoes(Posted 2012) [#31]
The loadstring OOM is coming from the stringbuilder. It's interesting that you say the file is 888KB and yet the allocation is over 2MB. Most implementations don't do more than double the buffer size if an append exceeds the existing allocation. I might have a poke around later.

The fact that the allocation is failing with 10MB free suggests that you have a real issue with fragmentation though. Somewhere in your code you must be interweaving allocations of short and long-lived objects. That's not something I can offer any simple solutions to on a forum, unfortunately. I'll have to have a think about the problem as for all I know I could have the same problem!

The texture thing looks like images aren't actually being loaded to video memory. Are you only seeing this on the Wildfire or on lots of different phones?


AdamRedwoods(Posted 2012) [#32]
Sometimes though the images aren't blank they are other random images, stretched and distorted. It often happens to the font as well.

I would double-check that your images are being reloaded after android loses context.


siread(Posted 2012) [#33]
Ah, it seems your solution doesn't load jpegs on some devices (Samsungs), muddy. Gonna try just dropping it in the (hicolor_textures && hasAlpha) section instead.

Incidentally, am I going mad or has Mark made a mistake with his if/else in that section. Surely it should be checking !hicolor_textures. ie...
		if( hicolor_textures && hasAlpha ){
		}else if( hicolor_textures && !hasAlpha ){
		}else if( !hicolor_textures && hasAlpha ){
		}else if( !hicolor_textures && !hasAlpha ){
		}



siread(Posted 2012) [#34]
Good news. I released an update and things seem to be stable across all platforms. Thanks again muddy_shoes. :)


muddy_shoes(Posted 2012) [#35]
So your code now uses GLUtils for RGBA8888, but the existing solution for the rest?

Can you describe what "not working" meant on Samsung devices? Did it crash or were the images empty or wrongly coloured?


siread(Posted 2012) [#36]
Yeah, I just placed it here:
if( hicolor_textures && hasAlpha ){
	//RGBA8888...
		
	GLES11.glTexImage2D( GLES11.GL_TEXTURE_2D, 0, hasAlpha ? GLES11.GL_RGBA : GLES11.GL_RGB, 
texwidth, texheight, 0, hasAlpha ? GLES11.GL_RGBA : GLES11.GL_RGB, GLES11.GL_UNSIGNED_BYTE, null );
        
	GLUtils.texSubImage2D(GLES11.GL_TEXTURE_2D, 0, 0, 0, bitmap);
}


And left the rest. Not perfect because I guess 1024x1024 jpgs would cause the same issue as before but I don't use any.

My jpgs are just used for background images and on Samsung Galaxy S2 and Nexus devices the bgs were all black...

http://www.newstargames.com/newstarforum/attachment.php?attachmentid=2239&d=1333544088


Shockblast(Posted 2014) [#37]
Sorry for reviving an old topic but I am wondering if Mark has incorporated this solution in the code yet? At first glance at the Android target source code, it seems that Mark has already incorporated it. But I am still getting some out of heap errors from users.

Is there anything else that can be done to reduce this error? It happens most of the time when the game loses focus due to an advertisement or when pressing the home button then going back to the game several times just like siread describes. I did read in this topic that not using a texture atlas might solve it... but a texture atlas has lots of other advantages...


muddy_shoes(Posted 2014) [#38]
The mojo code is essentially unchanged in 77d as far as I can tell from a brief look. There's some "experimental" version on Bind in there, but it's not called.