I think that we came up with a good compromise that maximizes backwards compatibility while maintaining the ease of use for the programmer and keeping maximum flexibility for the future.
The idea goes like this:
throw statements would keep the same syntax; you can throw anything you want.
However, the throw arguments will be mapped in a systematic way to the exception hash (I mean the automatic catch variable we always called “$ex”).
the exception hash would have the following keys as before:
next (for chained exceptions)
and additionally would have the following new keys which would be populated depending on the throw arguments:
if the throw statement is a single value of any type, it’s mapped to $ex.err
If it’s a list, elements 0 and 1 are mapped to $ex.err and $ex.desc, whereas any further elements (or the rest of the list if there are more than 3) are mapped to $ex.arg
This means that no throw statements would have to be changed, only catch blocks (most of these should be in OM/Qore anyway, so it’s no problem).
Also for other applications that would like to throw only an integer, this would still be possible – throw 400; would just map to $ex.err == 400 with $ex.desc and $ex.arg set to NOTHING.
System exceptions would always have $ex.err and $ex.desc populated.
As before, there would be no automatic $argv assignment, and if you don’t put a single variable name in the catch block, you can’t access the exception information.
A rethrow statement will be executed which will allow the exception to be rethrown: rethrow $ex;