Free Memory woes
|
|
Synergy Belvedere
Prim Reaper
Join date: 7 Jul 2004
Posts: 253
|
05-09-2005 16:03
Hi all, I've been working on a large script for about 3-4 months now (limited spare time) I ran into Stack-Heap Collision today  I know it means that my script has become too large, and that I should use linkset messages to divide it into smaller scripts that pass each other parameters. Problem is, omg I'm thinking it's going to take forever to rewrite all this code to do that! It's basically setup this way: DECLARE CONSTANTS DECLARE VARIABLES FUNCTIONS (about 12 of them) State Default Listen() About 15 listen events it handles Is there an easy way to get this coded over to split scripts? Most of the listen if() statements call a function directly in the script, and if I split all the functions off to another script, that's gonna be messy. As well, will I have to declare the constants in both scripts ? What about global variables? My brain hurts, plz help 
_____________________
---------------------------------------------------------- --The mind's eye is limited only by its focus--
|
|
Jeffrey Gomez
Cubed™
Join date: 11 Jun 2004
Posts: 3,522
|
05-09-2005 16:17
Show us the code. 
_____________________
---
|
|
Synergy Belvedere
Prim Reaper
Join date: 7 Jul 2004
Posts: 253
|
05-09-2005 16:19
Sorry Jeffrey, I'm afraid I can't do that. Been working too hard on this to have some yahoo snag it 
_____________________
---------------------------------------------------------- --The mind's eye is limited only by its focus--
|
|
Jeffrey Gomez
Cubed™
Join date: 11 Jun 2004
Posts: 3,522
|
05-09-2005 16:55
All I can suggest, then, is that you split off a few of the functions with link messages.
_____________________
---
|
|
Synergy Belvedere
Prim Reaper
Join date: 7 Jul 2004
Posts: 253
|
05-09-2005 22:31
Sigh, back to square one.
_____________________
---------------------------------------------------------- --The mind's eye is limited only by its focus--
|
|
Catherine Omega
Geometry Ninja
Join date: 10 Jan 2003
Posts: 2,053
|
05-10-2005 00:25
From: Synergy Belvedere Sigh, back to square one. It doesn't have to be. You can break almost any script up fairly effortlessly. If you're getting a stack-heap collison, it's because your script is storing data, correct? Someting to do with the listens, I'm guessing? Would it be possible to break your script up into two sections, one that listens, then passes a message to the second, that does whatever is producing the list or string that's filling up your memory space? It's hard to know what you're attempting to do, though... is there any way you could post a more detailed description of what the script does?
|
|
Strife Onizuka
Moonchild
Join date: 3 Mar 2004
Posts: 5,887
|
05-10-2005 01:43
May i ask what the script is to do?
It may have already been solved by another.
_____________________
Truth is a river that is always splitting up into arms that reunite. Islanded between the arms, the inhabitants argue for a lifetime as to which is the main river. - Cyril Connolly
Without the political will to find common ground, the continual friction of tactic and counter tactic, only creates suspicion and hatred and vengeance, and perpetuates the cycle of violence. - James Nachtwey
|
|
Zonax Delorean
Registered User
Join date: 5 Jun 2004
Posts: 767
|
05-10-2005 02:46
I saw a scriptFS in the forums, maybe try using that. Yes, that still means SOME parts of the script have to be rewritten. And yes, I DO know how painful it is to rething the code and rewrite it all because of limits -- I have been there  Besides, SL seems to be very slacky with memory things -- some things just seem to use way more memory than they ought to.
|
|
Caoimhe Armitage
Script Witch
Join date: 7 Sep 2004
Posts: 117
|
05-10-2005 07:46
From: Zonax Delorean I saw a scriptFS in the forums, maybe try using that. I wrote that  From: Zonax Delorean Besides, SL seems to be very slacky with memory things -- some things just seem to use way more memory than they ought to.
You have no *idea*. I did some very rough measurements using llGetFreeMemory() (which has it's own troubles to be sure) and found that string list entries had something in excess of 40 bytes of overhead! I actually remember a higher number from some tests, but I can't believe the number I remember. The short form is that I find that I can store around 70(!) AV name/key pairs in the SFS before it runs out of heap. In another test I have a bunch of objects working out their relative geometry in-world, and I couldn't even manage to work with 16 objects because of the copies required during list sorting! Solving *that* problem has required a totally different (and *much* less traightforward) approach to the problem. We desparately need more memory for our scripts... - C
|
|
Synergy Belvedere
Prim Reaper
Join date: 7 Jul 2004
Posts: 253
|
05-10-2005 08:24
Amen to that Caoimhe Like I said, I cant post the actual script, but long story short it's a game. The script that's running out of memory is the scoreboard. It listens for things happening in the game and responds appropriately. It's all done over private channels so no open chat lag. So here's the real question, say the listen event handles a score like so if(msg=="ADDNEWPLAYER") { if(CheckTeams()) //checkteams is a custom function that returns true or false { llSay(0,"Player has been added"); } }
Now, if I want to move all my functions to a new script (seems like that'd be the easiest) and call them from this existing script, how would I go about handling functions that return items, like "checkteams()" above ? And what is ScriptFS? Also, what do I do about global variables? I'm sure script 2 wont see the global vars (and constants for that matter) that I setup in script 1.
_____________________
---------------------------------------------------------- --The mind's eye is limited only by its focus--
|
|
Caoimhe Armitage
Script Witch
Join date: 7 Sep 2004
Posts: 117
|
05-10-2005 08:52
From: Synergy Belvedere Like I said, I cant post the actual script, but long story short it's a game. The script that's running out of memory is the scoreboard. It listens for things happening in the game and responds appropriately. ... Now, if I want to move all my functions to a new script (seems like that'd be the easiest) and call them from this existing script, how would I go about handling functions that return items, like "checkteams()" above ? Also, what do I do about global variables? I'm sure script 2 wont see the global vars (and constants for that matter) that I setup in script 1.
yup. Globals are evil. You need to split the script up into independent subsystems that do not share state. this can be easy or hard. Essentially you have to hand-code RPCs between your split scripts. This can be very tedious if you have complicated stateful interactions. I generally end up with a master control script, and several slaves which accomplish various effects. It's hard to say more without seeing your code. And oh yes - you code your RPC using llMessageLinked(). A prim can't hear it's own chat messages. - C
|
|
Synergy Belvedere
Prim Reaper
Join date: 7 Jul 2004
Posts: 253
|
05-10-2005 08:59
Well fortunately ( or maybe not lol ) the script has no states except default. All flow control is done within the listen event.
If you're in game I'd be willing to show you the script on a one on one basis, but I dont want to post it publicly. I'm almost always on, so IM me in world if you're up for it (would greatly appreciate it )
_____________________
---------------------------------------------------------- --The mind's eye is limited only by its focus--
|
|
Laukosargas Svarog
Angel ?
Join date: 18 Aug 2004
Posts: 1,304
|
05-10-2005 09:04
I believe llGetFreeMemory() is a misnomer or at the very least buggy! It doesnt return the current free memory, it seems to return the least amount of memory that was EVER available to the script. For example: deleting items in lists does not appear to free memory back to the script according to llGetFreeMemory(). The only way to free the used memory appears to be to reset the script. I'd love someone to confirm or put me right on this.
|
|
Jon Marlin
Builder, Coder, RL & SL
Join date: 10 Mar 2005
Posts: 297
|
05-10-2005 09:43
I don't have any inside knowledge, but I suspect the scripting engine uses a simple garbage collector, that runs at a low priority. What that means is the memory does get cleaned up, just not necessarily the instant it is no longer referenced.
I can't imagine any other way that would let you do the kinds of list operations LSL lets you do, with globals.
- Jon
|
|
Laukosargas Svarog
Angel ?
Join date: 18 Aug 2004
Posts: 1,304
|
05-10-2005 10:00
From: Jon Marlin I don't have any inside knowledge, but I suspect the scripting engine uses a simple garbage collector, that runs at a low priority. What that means is the memory does get cleaned up, just not necessarily the instant it is no longer referenced. ..snip Have you seen this happen ? I'm not convinced it's cleaned up until the script is reset. I've got debug code in a script that needs ( would desperately like to ) release memory when done with lists. The figures never change. And the said scripts have been running for a few weeks now. All llGetFreeMemory ever returns is the least amount that was available in the past.
|
|
Jon Marlin
Builder, Coder, RL & SL
Join date: 10 Mar 2005
Posts: 297
|
05-10-2005 10:44
From: Laukosargas Svarog Have you seen this happen ? I'm not convinced it's cleaned up until the script is reset. I've got debug code in a script that needs ( would desperately like to ) release memory when done with lists. The figures never change. And the said scripts have been running for a few weeks now. All llGetFreeMemory ever returns is the least amount that was available in the past. I haven't seen it happen, but you could easily test it: - make a script that sets a 1 second timer - have a global list that contains 10 strings ("one" through "ten" or something like that) - every second, re-sort the list descending and then ascending - print the free memory - add something like a touch to toggle it on and off Every time you sort a list, LSL creates a new list with the items in it. The old list has to go somewhere, and I suspect it will get garbage collected. I'm at work, so I can't try this now, but it would be worthwhile knowing. - Jon
|
|
Synergy Belvedere
Prim Reaper
Join date: 7 Jul 2004
Posts: 253
|
05-10-2005 16:50
list mylist=["1","2","3","4","5","6","7","8","9","10"]; integer on=TRUE; default { state_entry() { }
touch_start(integer total_number) { if(on){llSay(0, "off");on=!on;llSetTimerEvent(0);} else{llSay(0,"on");on=!on;llSetTimerEvent(1);} } timer() { llListSort(mylist,0,TRUE); llListSort(mylist,0,FALSE); llWhisper(0,(string)llGetFreeMemory()); } }
Prints free memory as 15,600 on each pass. FYI
_____________________
---------------------------------------------------------- --The mind's eye is limited only by its focus--
|
|
Jon Marlin
Builder, Coder, RL & SL
Join date: 10 Mar 2005
Posts: 297
|
05-10-2005 17:41
From: Synergy Belvedere Prints free memory as 15,600 on each pass. FYI
That is as I would expect. The memory taken by the list that you sorted is clearly being deallocated automatically, which is in essence what a garbage collector does. - Jon
|
|
Synergy Belvedere
Prim Reaper
Join date: 7 Jul 2004
Posts: 253
|
05-11-2005 07:53
Ok mananged to get the script split into 2, 7292 free memory in the main script yay! *clap* Globals are proving to be real fun, they're so intertwined into my listen event and my functions that i'm gonna have to pass them as well. This certainly slows the game a bit, but overall I'm happy with the progress (only took an hour to split the script and get it to compile). Thx all for your help. -Syn 
_____________________
---------------------------------------------------------- --The mind's eye is limited only by its focus--
|
|
Jon Marlin
Builder, Coder, RL & SL
Join date: 10 Mar 2005
Posts: 297
|
05-11-2005 08:03
From: Synergy Belvedere list mylist=["1","2","3","4","5","6","7","8","9","10"]; integer on=TRUE; default { state_entry() { }
touch_start(integer total_number) { if(on){llSay(0, "off");on=!on;llSetTimerEvent(0);} else{llSay(0,"on");on=!on;llSetTimerEvent(1);} } timer() { llListSort(mylist,0,TRUE); llListSort(mylist,0,FALSE); llWhisper(0,(string)llGetFreeMemory()); } }
Prints free memory as 15,600 on each pass. FYI Actually, I just realized that there's a mistake in your script (well, to be more specific, it doesn't really do what I intended, which is understandable given that I didn't specify it correctly). You need to change the sort lines to look like: mylist = llListSort(mylist,0,TRUE); mylist = llListSort(mylist,0,FALSE);
- Jon
|
|
Kyrah Abattoir
cruelty delight
Join date: 4 Jun 2004
Posts: 2,786
|
05-11-2005 08:10
From: Laukosargas Svarog I believe llGetFreeMemory() is a misnomer or at the very least buggy! It doesnt return the current free memory, it seems to return the least amount of memory that was EVER available to the script. For example: deleting items in lists does not appear to free memory back to the script according to llGetFreeMemory(). The only way to free the used memory appears to be to reset the script. I'd love someone to confirm or put me right on this. i think the memory used by a list isnt freed until the list has been destroyed (if its a global one your a fucked up)
_____________________
 tired of XStreetSL? try those! apez http://tinyurl.com/yfm9d5b metalife http://tinyurl.com/yzm3yvw metaverse exchange http://tinyurl.com/yzh7j4a slapt http://tinyurl.com/yfqah9u
|
|
Escort DeFarge
Together
Join date: 18 Nov 2004
Posts: 681
|
05-11-2005 08:36
From: Kyrah Abattoir i think the memory used by a list isnt freed until the list has been destroyed (if its a global one your a fucked up) mylist = []; appears to do the trick for me... *edit - but lauko is right, llGetFreeMemory() does not change the value reported after releasing the memory* /esc
_____________________
http://slurl.com/secondlife/Together
|