getopts problem

i was going through the man page of getopts

this particular section is not clear to me can anyone please
clarify in a little detail so that i can understand the concept

MANPAGE::

Since getopts affects the current shell execution environ-
ment, it is generally provided as a shell regular built-in.
If it is called in a subshell or separate utility execution
environment, such as one of the following:

       \(getopts abc value "$@"\)
        nohup getopts ...
        find . -exec getopts ... \\;

 it does not affect  the  shell  variables  in  the  caller's
 environment.

 Notice that shell functions share OPTIND  with  the  calling
 shell  even  though  the  positional parameters are changed.

I am not sure which point you have troubles to understand, so maybe my explanation is superficial - i'll just give it a try:

when you call a script with some parameters these parameters are part of the scripts environment - variables $1, $2, $3, .... - and this environment does not change under normal circumstances (save for explicit changes to it using the "shift" keyword, etc.).

This now changes when you use "getopts" to parse the commandline. "getopts" will do the parsing but after calling it the environment (more precisely: part of it - the parameters special variables) will have no more meaningful content. Example:

echo "$1"      # some content
/some/command
echo "$1"      # same !! content as before

whereas:

echo "$1"      # some content
getopts [.....] "$@"
echo "$1"      # NOT the same content as before

To prevent this it is possible to call getopts in a different (child) environment by several means listed in the manpage. When you call a child process the environment of the father process is copied and given to the child (the child "inherits" from the father) - this is why the Nr. 1 reason for cron jobs is the wrong environment: the job is tested in a login shell, which has some environment the inheriting job relies implicitly upon. When it is called not by the login shell but by cron (which has next to no environment, not even a PATH) it fails. This only as n aside.

When getopts is - by the mentioned means - called in a child process it gets a copy of the environment and works on this, therefore not destroying the father process' environment.

Was this your problem or is there more to it?

I hope this helps.

bakunin

thanks, that pretty much explained and cleared my confusion ...

as it seems to me you can help can you tell me please in the below code what this set lines are doing

set -- -1 -----------> ??
while getopts 1 opt; do
case "${opt}" in
1) echo "Worked!";;
*) exit 1;
esac
done

OPTIND=1
set -- -2-------------??
while getopts 2 opt; do
case "${opt}" in
2) echo "Worked!";;
*) exit 1;
esac
done

hello bakunin,
i tried something after reading your post ...there is a problem..
see below please

*************************CODE**********************

echo $1 $2 $3

while getopts ":ab:" var
do
case $var in

a) echo "option a"
;;

b) echo "option b argument $OPTARG "
;;

esac
done

echo " $1 $2 $3"

**********************o/p*******************
csbu061 [mhalder] 216: bash sample.sh -b malay milan manab
-b malay milan manab
option b argument malay
-b malay milan

 ----according to yoy the envirinment [$1..$2..] will change if i call from the same shell but here it is printing the same values.

in the below code what this set lines are doing ???
and what does this -- variable means

set -- -1 -----------> ??
while getopts 1 opt; do
case "${opt}" in
1) echo "Worked!";;
*) exit 1;
esac
done

OPTIND=1
set -- -2-------------??
while getopts 2 opt; do
case "${opt}" in
2) echo "Worked!";;
*) exit 1;
esac
done
Edit/Delete Message

in the below script i am expecting the variable surname to be changed but that is not happening can anyone help and explain why and how to do that

surname=halder

echo $surname

while getopts ":b:" OPTION
do
case $OPTION in

b) surname=bose
;;

esac
done

echo $surname

The point is not that it has to change, but it might change. You simply cannot rely on the fact that "$1" remains the same before and after getopts - whereas you can rely on, say, "$charley" being the same before and after executing a command.

The meaning of the set-command is simple: "set --" clears the special variables "$1", "$2", etc.:

# cat settest.sh
#!/bin/ksh

echo "first parm is: $1"
echo "second parm is: $2"
echo "third parm is: $3"

set --

echo "first parm is: $1"
echo "second parm is: $2"
echo "third parm is: $3"
exit 0

# ./settest.sh a b c
first parm is: a
second parm is: b
third parm is: c
first parm is:
second parm is:
third parm is:

Therefore the "set -- -2-------" means: first make sure no other commandline parameter is set, regardless of what you enter on the commandline, then set exactly one parameter ("-2") with some argument ("------").

I hope this helps.

bakunin

hello bakunin,

can you please tell me about the next problem of printing the
var that i have posted