Code:
#test.sh
test_func(){
var1="$1"
var2="$1"
echo "var1 before typeset: $var1"
echo "var2 before typeset: $var2"
typeset -l var1="$1"
typeset -l var2
echo "var1 after typeset: $var1"
echo "var2 after typeset: $var2"
}
test_func "$1"
var1="$1"
var2="$1"
echo "var1 before typeset: $var1"
echo "var2 before typeset: $var2"
typeset -l var1=$1
typeset -l var2
echo "var1 after typeset: $var1"
echo "var2 after typeset: $var2"
output using bash with input SAMPLE_INPUT:
var1 before typeset: SAMPLE_INPUT
var2 before typeset: SAMPLE_INPUT
var1 after typeset: sample_input
var2 after typeset:
var1 before typeset: SAMPLE_INPUT
var2 before typeset: SAMPLE_INPUT
var1 after typeset: sample_input
var2 after typeset: SAMPLE_INPUT
output using ksh:
var1 before typeset: SAMPLE_INPUT
var2 before typeset: SAMPLE_INPUT
var1 after typeset: sample_input
var2 after typeset: sample_input
var1 before typeset: sample_input
var2 before typeset: sample_input
var1 after typeset: sample_input
var2 after typeset: sample_input
I dont understand why bash clobbers var2 in a function and why ksh changing the variable inside a function affects the value of it outside the function when re grabbing the value from $1. I assume this has something to do with their implementation of local vs global variables.
my desired output would be the same on bash and ksh and inside/outside of a function:
var before typeset: SAMPLE_INPUT
var after typeset: sample_input
used out of function:
var before typeset: SAMPLE_INPUT
var after typeset: sample_input
In bash, typeset
is an alias for declare
, which makes variables local when invoked inside a function unless the argument -g
is added.
In ksh, typeset
has different behavior depending on how you defined your function: With test_func() { ... }
variables created with typeset
are global; with function test_func { ... }
they're local. Because you're using the test_func() {
syntax, in your ksh code, typeset
refers to the preexisting global variable instead of creating a local; so the original value is retained.
If you want identical behavior, you need to move typeset
outside of the function, or add -g
when the shell is bash; the latter can be done with a parameter expansion that emits -g
only when BASH_VERSION
is set, as below:
test_func(){
var="$1"
echo "var before typeset: $var"
typeset ${BASH_VERSION+-g} -l var="$1"
echo "var after typeset: $var"
}
var="SAMPLE_INPUT"
test_func "$var"
echo "var after function: $var"
...properly emits:
var after function: sample_input
...even on bash.
As for the empty value, you get that even on ksh if you change your function declaration syntax to make typeset
create locals by default:
function test_func {
typeset -l var
var="$1"
}
test_func "SAMPLE_INPUT"
echo "Result is: <$var>"
...emits, Result is: <>
when run in ksh.