When we reduced the scope of the try block in commit a823158, we introduced a bug because the tree modification was attempted even if no value was assigned (when the exception was triggered). Returning when the function is not computable ensures that this won't happen.
Scaringly, there was no check that caught this.
We had a big chaos with type conversion. That caused a bug where passing a key to a function that required a string, or vice versa, crashed the script.
Diminish the chaos by modifying the parameters just prior to invocation (in lslfoldconst). We also remove the, now unnecessary, calls to force floats, either alone or within vectors or quaternions.
Commit 5804a9a introduced a bug where having the foldtabs option disabled (normal) prevented optimizations of functions. Fix it for good (hopefully). While on it, rename the nofoldtabs option to warntabs, making it default, and use it to disable a warning when there are tabs in a string.
When a function folds to a string that contains a tab, e.g. llUnescapeURL("%09"), or to a list that contains a string that contains a tab, a warning is emitted unless the foldtabs option (which forces the optimization) is used. This option allows to quiet the warning without forcing the optimization.
Resolving some constant function calls may generate tabs, e.g. llUnescapeURL("%09"). That can't be pasted into a script, and a warning is emitted. The warning text was misleading, making one think that something went wrong when all that happened is that an optimization couldn't be applied. Rewrite the text of the warning to be clearer about what the problem is.
- Move TODO of <0 to !=-1 to boolean, as it's counter-productive otherwise.
- All a!=b except list!=list are equivalent to !(a==b).
- Change a>b to b<a to simplify cases to analize.
- Proper fall-through in some spots, or return in some others where it didn't apply.
- Simplify handling of a<-2147483648 as a&0, falling through, instead of coping with it ourselves.
This allows better side-effect analysis, because 'return' is not side-effect free unless it's the last statement. But that's better handled in the dead code removal module, as the comment specifies.
Adds a new tree node type, SUBIDX, which hopefully should never appear in actual output. If it does, it's prefixed with the string (MISSING TYPE) as a cue to the programmer.
This obviates the need for (-a)*(-b) because it will be simplified automatically. It also enables (a+1)*b-1 to be simplified to just ~(~a*b). Still missing simplifying a*b+b to (a+1)*b, but that's more complicated.
a != -1 is now optimized to ~a in conditions. a == 1, a != 1, etc. are all optimized. a||b -> a|b is done. a^0, a^-1 are optimized. a&&b is transformed to !(!a|!b), but not yet into a&b when possible.
The output module adds parentheses where necessary, depending on the evaluation order in the tree. Or that's the idea. Prone to bugs, let's see how it bodes.