Tek-Tips is the largest IT community on the Internet today!

Members share and learn making Tek-Tips Forums the best source of peer-reviewed technical information on the Internet!

  • Congratulations SkipVought on being selected by the Tek-Tips community for having the most helpful posts in the forums last week. Way to Go!

Using Signal and TWO-WAY pipe to cd login shell from another script

ksh Inter-process comm's

Using Signal and TWO-WAY pipe to cd login shell from another script

by  mi294r3  Posted    (Edited  )
How can I change the current directory from a script.

This question seems to pop up in the forum occasionally.

One way is to source the script into the current shell.
For example scriptname changedir
Then from the prompt

[tt][color green]-> . changedir[/color][/tt]

The risk is anything done by the script, is done to the login shells environment.

A way to change the current directory from another shell is the use of signals and pipes.

This example was written and tested on AIX 5.3 using Korn Shell. There may be some issues that might require some tweaking, however the concept is sound and can be applied to variety of problems.



First create a pipe in your home directory
At the prompt
[tt][color green]-> mknod .Can_and_String p[/color][/tt]
-----------------
Then make the following entry in your .profile
_________________________________________________________
[tt][color blue]
func51 ()
{
while read Msg
do
if echo ${Msg}|grep -q "^REQ_TO_LOGIN_SHELL"; then
eval $(echo ${Msg}|cut -d: -f2)
fi
break
done <$HOME/.Can_and_String
}

trap "func51" 51
export LOGIN_SHELL=$$[/color][/tt]
____________________________________________________________

The function definition func51 is loaded into memory when .profile is sourced. The function is executed when a SIGNAL 51 is sent to the login shell.
This is where the trap command comes into play
[tt][color green]trap "func51" 51[/color][/tt]
Simply put, it says trap ANY signal 51 sent to the current shell, and when you do run func51.
I used signal 51 becasue it is undefined at my location, I did not explore using any other signals. What you decide to use will be based on your environment.
The function reads from the pipe .Can_and_String, looks for any string staring with REQ_TO_LOGIN_SHELL. When it finds one, it assumes the string is a 2 field string seperated by a colon. The second field is a command that another process is requesting the login shell to execute.
----------------------------
Next create a small shell script called R2loginShell, it should have the following two lines;
___________________________________________________________
[tt][color blue]kill -51 ${LOGIN_SHELL}
echo "REQ_TO_LOGIN_SHELL:$@" >>$HOME/.Can_and_String[/color][/tt]
___________________________________________________________
This script sends signal 51, (via the kill command) to the process ID of the login shell. It then writes a request, for the login shell, to the pipe .Can_and_String. The actual command is sent from another script.
-----------------
The last thing to do is to write a script that utilizes the process you just put in place. The example I used was the following script called cdmenu
___________________________________________________________
[tt][color blue] select CHOICE in /tmp /etc /usr /var EXIT;
do
if [[ ${CHOICE} = 'EXIT' ]] then
exit
fi
$HOME/R2loginShell cd ${CHOICE} &
clear
break
done [/color][/tt]
___________________________________________________________
This script builds a menu with 5 selections.
[tt][color green]1) /tmp
2) /etc
3) /usr
4) /var
5) EXIT
#? [/color][/tt]
Except for EXIT, when a selection is made, R2loginShell is started in the background. The call has 2 positional parameters 1)cd & 2)the value of the option selected.
For example if you selected 2;
[tt][color green]1) /tmp
2) /etc
3) /usr
4) /var
5) EXIT
#? 2 [/color][/tt]

the call to R2loginShell cdmenu is resolved to this

[tt][color blue]R2loginShell cd /etc[/color][/tt]

the positional parameters are then read into the pipe .Can_and_String via [tt]$@[/tt]
______________
[tt][color blue]
echo "REQ_TO_LOGIN_SHELL:$@" >>$HOME/.Can_and_String[/color][/tt]
____________

Give it a try?
[morning]JRjr
Register to rate this FAQ  : BAD 1 2 3 4 5 6 7 8 9 10 GOOD
Please Note: 1 is Bad, 10 is Good :-)

Part and Inventory Search

Back
Top