Jump to content
Sign in to follow this  
Nutty_101

Is there a limit in the compiler?

Recommended Posts

Does anyone know what the max length is for a string in Armed assault? I am loading in some large scripts and starting to see that they fail due to being cut off. So it has to be something with the size of strings.

Anyone know about this?

<table border="0" align="center" width="95%" cellpadding="0" cellspacing="0"><tr><td>Code Sample </td></tr><tr><td id="CODE">

_ScriptText = Loadfile "SomeScript.Sqf";

_Town = format[_ScriptText,"%1","%2","%3","%4","%5","%6","%7","%8","%9","%10","ATOWN"];

_TownArray spawn (compile _Town);

Share this post


Link to post
Share on other sites
AFAIK the limit is 2038 characters.

Doh! Oh well that answers my question. Gonna have to get creative.

Share this post


Link to post
Share on other sites

Interesting use of the format command there; I haven't seen that done before.

Anyway, is there a reason you can't just pass extra parameters in via _this, instead of using format?

The only reason I can see you using format like that is to "pass" the name of a variable in to your script. If that is the case, a better solution might be to simply use one global array, instead of a bunch of individual global variables. Then you'd just need to pass an array index in thru _this (this is better on the CPU anyway; hence one of the reasons ECP changed to doing this in OFP).

If you don't want to do that, or I'm completely off base, then just pass strings in via _this, and use the call or format command inside of your script to evaluate them as the script is run.

Share this post


Link to post
Share on other sites

Just to clarify. The scripts can be as (practically) large as you want, (eg: 30k is fine), but in this case, you are probably limiting yourself by assigning the script to a string.

If you _really_ want to do it that way, you might get some more milage out it by using preprocessFile rather than loadFile to strip out any unneeded comments.

But it sounds like you simply need to switch to using parameters instead or utilise #define macros.

Share this post


Link to post
Share on other sites

The problem is that the scripts dont exist on the hard drive. They are on another server in a MySql database. I pull them into the system and use the format command to modify the scripts to support globals. Unless i am offbase you cannot pass a global via the _this and be able to update it. Thats what the format command is being used for.

This is done so i only have to modify one script that can be used for several areas that utilize separate globals that get publicvariable'd to clients.

I have a work around for the format function now, though i still run into the string issue. I just used a function to change the string before it makes it to armed.

Share this post


Link to post
Share on other sites

I guess i can go back to the old method. I used to have the program write the scripts to a file on the system upon calling them. Oh well.

Share this post


Link to post
Share on other sites
Quote[/b] ]Unless i am offbase you cannot pass a global via the _this and be able to update it. Thats what the format command is being used for.

Interesting project. Anyway, you *can* do this, just in a slightly different manner.

The trick is to pass the variable names into the script as strings in _this.

["myvar1","myvar2",...] execVM "script.sqf"

When you want to use the variable, *that* is when you use the format command, combined with the call command:

_myvar1 = _this select 0;

private "_currentValue";

call compile format ["_currentValue = %1", _myvar1];

//_currentValue now holds whatever "myvar1" held at this time

call compile format ["%1 = damage player", _myvar1];

//"myvar1" now holds the damage of the player

This is similar to the trick you were using before, only now the formatting takes place while the script is run, not when it is loaded. Oh, and no crashes from large strings.

Share this post


Link to post
Share on other sites

That will work, I was only using it for catching the values thru the private command and returning the values. Just wish there was a way to store larger strings in the system.

I have gone back to dumping the scripts to a file on the hard drive. Kinda sucks as it defeats the purpose to a degree but it works. I am still able to terminate the scripts as required. So the main reason for this is working as planned. Makes it so i no longer have to kill the server to modify any scripts.

Share this post


Link to post
Share on other sites

Is there yet a definitive answer to this question?

The wiki still states that there is NO effective limit to string size in ArmA, but that OFP was limited to 2056 characters.

So: is there a limit to string length in ArmA's underlying code?

Is there a limit to string length when publicVariable'd?

Enquiring minds wish to know..

Share this post


Link to post
Share on other sites

master Sickboy says

Quote[/b] ]tried: _str=""; _i=0; for "_x" from 1 to 9999 do { _str=(_str+str(_i));_i=_i+1;if(_i>9)then{_i=0}} ?

you can also try to generate an array with 5000 entries, then make a string from that, then call compile it back to an array and see if its still a valid array and you still have the amount of entries, in that case, the string would've been 5000+5000+2 long smile_o.gif

2= [ and ], one times 5000 for the entries, and one times 5000 for the commas) or maybe 4999 not sure now smile_o.gif

yes, 5000+4999+2

smile_o.gif

Share this post


Link to post
Share on other sites
Quote[/b] ]So: is there a limit to string length in ArmA's underlying code?

I could not be bothered finding the actual limit, but you can have more than 2038 characters. The limit being enforced could be down to the Format command? In OFP using Format with a large string would cause a CTD.

Any way, I tried this as a quick test:

<table border="0" align="center" width="95%" cellpadding="0" cellspacing="0"><tr><td>Code Sample </td></tr><tr><td id="CODE">_Count=0;

_Str="[";

While {_Count<20000} Do

       {

       _Str=Str+"1111111111,";

       _Count=_Count+1;

       };

_Str=Str+"1111111111]";

Hint Format ["Count %1",Count (Call Compile _Str)];

The above code will return an array count of 20001 elements. So that’s just about 20001*11 characters in _Str without any problems so far.

If it is down to the format command, you could store your scripts in arrays, written into functions. For example:

MyScript.sqf:

<table border="0" align="center" width="95%" cellpadding="0" cellspacing="0"><tr><td>Code Sample </td></tr><tr><td id="CODE">[

"_Count=0;",

"_Str=""["";",

"While {_Count<20000} Do",

"{",

"_Str=Str+""1111111111,"";",

"_Count=_Count+1;",

"_Str=Str+"1111111111]";"

]

So then you would have something like:

<table border="0" align="center" width="95%" cellpadding="0" cellspacing="0"><tr><td>Code Sample </td></tr><tr><td id="CODE">_Source=Call Complile LoadFile "MyScript.sqf";

_Output="";

{_Output=_Output+_x} ForEach _Source;

_pScript=[] Spawn (Compile _Output);

Like I said, I only did a quick test. Also not sure how this will fit into what your actually trying to do.

Share this post


Link to post
Share on other sites

The 2000something limit is indeed on the output of the format command, the strings itself can be much larger. If you need to use format to output longer than the limit, then you can split it into smaller chunks and add them together, ie. with '_str = format[...] + format[...]' and there should be no problems.

Share this post


Link to post
Share on other sites

lol, UNN UR a mindreader.

Thanks for replies guys.

Now all I need to find is a way to specifically target a single client for receipt of a (large) string, just tested some more and > 256K is possible, even publicVariable'd!

What I want to do is send the code-containing string in array dynamically to specific / connecting clients - there is a real good reason for this to happen, however so far all I can see the possibilities of are the onPlayerConnected and publicVariable commands would cause a re-send of the code to ALL pre-existing clients in a JIP scenario. No good if the string is large and you want to avoid red chains...

So: IS there ANY way to send a string to a specific client or the newly-joining player ONLY? I have never seen this done, nor read of a way to do it. But for this idea to work then it will be needed, even without the string slicing this idea could work okay...

Share this post


Link to post
Share on other sites

Please sign in to comment

You will be able to leave a comment after signing in



Sign In Now
Sign in to follow this  

×