> I'm fine if upper references to not-yet-defined variables aren't supported but I would very much prefer that this triggers an error rather than does something not defined. In my opinion undefined behaviors in programming languages are lazy and don't help anyone, neither the language users nor the language implementers.
You have a lot of bones to pick with the POSIX spec, then.
I know that the POSIX spec and the current Zsh spec contain many instances of undefined behavior, That is however not an excuse to add even more.
Regarding upper references to not-yet-defined variables, we should either say that they are not supported and report an error when any is defined or state that they refer to a future global variable that may be created by assigning to the reference and indicate that the creation by assignment will fail if a local variable with the same name already exists. The latter is the current behavior but since it's specified as undefined behavior users who discover it won't be sure whether they can trust it. With an explicit specification, the same behavior becomes much more useful; users can then rely on it.
Now, which of the two should we adopt? Let's consider the following function
function foo() {
typeset -nu ref=$1
typeset var=...
...
# Assign result to "ref" (and define a global variable if "ref" didn't already refer to an existing variable)
ref=...
}
What this function intends to do seems perfectly reasonable to me. The only downside is that it will fail in case it's called with "var" from a context where no variable named "var" is already defined. That's unfortunate but certainly not a reason to forbid the whole thing. Therefore I support keeping the current behavior. We should just document it properly.
A knowledgeable and forthcoming function author would document that the function should not be called with a not-yet-defined "var" variable name. However, chances are that this won't happen. In fact, chances are high that the function author won't even be aware of that shortcoming. That's why I think a run-time warning could be useful when such assignments fail.
You agree this is OK at the top level?
typeset -n globalref=undefinedglobal
Yes
If you agree, then does this generate an error?
() { typeset -un localref=globalref; ... }
It depends on how we specify upper references but I would rather lean toward the current behavior which allows it even for not-yet-defined variables.
Why would the following require an error?
() { typeset -un localref=globalvar; typeset -g globalvar; localref=val }
Indeed, there isn't really a reason/need to reject this. I would just properly document this behavior so that users don't have to discover it by themselves and also so that they can rely on it without fear that it may break in the future.
Philippe