Page 1 of 3 123 LastLast
Results 1 to 10 of 28

Thread: Using bash to conditionally stop an application.

  1. #1
    Join Date
    Jan 2008
    Beans
    53

    Question Using bash to conditionally stop an application.

    Specs:
    Ubuntu 11.04 64bit
    2.6.38-13-generic #56-Ubuntu SMP Tue Feb 14 12:39:59 UTC 2012 x86_64 x86_64 x86_64 GNU/Linux
    Using the Gnome desktop interface, and bash.

    My skill level with Bash:
    Somewhere between beginner and intermediate. I understand most of the basics, but not how to use all the basic concepts together very well.

    Condition:
    If VPN is active or inactive

    Requirement:
    If VPN is inactive, stop all programs that depend on the VPN being active.

    1st problem:
    If I start the programs that depend on the VPN from within the bash script the script essentially pauses until the program finishes or exits. This keeps me from being able to test whether the VPN is active or not.

    Possible solutions:
    I thought that maybe I could just make them separate processes and activate them manually once I was connected to the VPN. In this way I could run a script to check the connection status of the VPN and somehow trigger the programs to stop once the connection was lost but this raised a secondary problem.

    2nd Problem and questions:
    Once the VPN connection is lost, how can I tell a program to quit or exit nicely without killing it, and even if I have to kill it in order to stop it, how would I do that without being present since killing a program requires input from the user in the form of the super user password?


    Here is an example of the code I've been attempting so far. It functions in its current state with myprogram01 commented out, but it doesn't solve the problems I've mentioned above.
    Code:
    #!/bin/bash
    # The following might work as a conditional for programs that depend on the VPN in order to run or for programs that might need to stop running if the VPN is inactive.
    
    nmcli -p con up uuid #insert_connection_id #Attempt a connection to the VPN
    
    vpnstring=""
    vpnstring=`nmcli -t -f VPN con status |grep yes`
    	if [ "$vpnstring" = "yes" ]; then
    		echo VPN connection is active #dependency can be run here.
    		sleep = 5
    #		myprogram01			#this line stops the bash script from continuing. Consider maybe using a "watch" command???
    	else
    		echo VPN connection is inactive	#Possibly retry the connection in the loop below if not connected.
      fi
    #echo The contents of the vpn string are as follows.
    #echo $vpnstring
    
    while :
    do
      vpnstring=`nmcli -t -f VPN con status |grep yes`      #Executed as long as condition is true and/or, up to a disaster-condition if any.
    	if [ "$vpnstring" = "yes" ]; then
    		echo VPN connection is still active
    	else
      		echo VPN not connected.       	   #Possibly retry the VPN connection here.
    		break
      fi
    done
    Any advice?
    Thanks.
    Last edited by landstander; March 15th, 2012 at 06:37 PM.

  2. #2
    Join Date
    Mar 2012
    Location
    Russia
    Beans
    104
    Distro
    Ubuntu 11.10 Oneiric Ocelot

    Re: Using bash to conditionally stop an application.

    Code:
    #!/bin/bash
    VPNNAME=VPN1
    while true; do
    
    vpnstring=$(nmcli con status|grep -c $VPNNAME)
    program=programname
    
    date
    case $vpnstring in
    "0")
    echo "not connected"
    kill -SIGSTOP $program
    ;;
    "1")
    echo "VPN seems to work" 
    kill -SIGCONT $program
    ;;
    
    esac
    sleep 30
    
    done
    Something like this should do what you want.If i understand the problem. Sorry, can't test this.
    Last edited by CynicRus; March 15th, 2012 at 07:20 PM.

  3. #3
    Join Date
    Jan 2008
    Beans
    53

    Re: Using bash to conditionally stop an application.

    CynicRus,

    Thank you for the example it is very helpful and got me a lot farther towards getting this to work.

    I now have 2 scripts; vpn1.sh, and vpn2.sh
    (vpn1.sh): Attempt a connection until its successful then start a VPN dependant program.
    (vpn2.sh): Check the connection status of the VPN until the connection fails then stop the VPN dependant program that was started in Script 1.

    Error message generated by vpn2.sh:
    ./vpn2.sh: line 18: kill: myprogram01: arguments must be process or job IDs
    Note: Line 18 is as follows:
    kill -SIGCONT $program #Where $program is defined earlier in the code as myprogram01

    Checking process results:
    ~$ ps -aef |grep myprogram01
    13839 13789 1 18:06 pts/1 00:00:00 myprogram01
    13902 12683 0 18:07 pts/0 00:00:00 grep --color=auto myprogram01
    ~$

    Questions:
    1.) Why is myprogram01 not being recognized as a process when it is listed as one by "ps" from the command line?
    2.) How can I get around this problem, and is there a more elegant way other than parsing the job ID?
    Last edited by landstander; March 16th, 2012 at 02:30 AM.

  4. #4
    Join Date
    Jul 2007
    Location
    Poland
    Beans
    4,158
    Distro
    Ubuntu 10.04 Lucid Lynx

    Re: Using bash to conditionally stop an application.

    doesn't kill require PIDs not program names?

    you can try
    Code:
    kill -SIGCONT $(pgrep $program)
    pgrep does the same as ps | grep | cut_proper_column, but better

  5. #5
    Join Date
    Mar 2012
    Location
    Russia
    Beans
    104
    Distro
    Ubuntu 11.10 Oneiric Ocelot

    Re: Using bash to conditionally stop an application.

    program=`pidof myprogram01`

    kill -SIGCONT $program

  6. #6
    Join Date
    Dec 2011
    Beans
    621
    Distro
    Ubuntu 12.04 Precise Pangolin

    Re: Using bash to conditionally stop an application.

    Wish there was a more elegant way than
    Code:
    kill
    Or as an example:
    Code:
    236 vi ~/. bashrc
    or ! 236 to re-execute
    Other than that yeah; the job # because it is possible to run multipule commands in the background at the same time.

    Shame that the wildcards can't give us more functionalities or processes suitable for termination in a more ginger way- ( if I find anything; I'll post it )
    It's worth investigating another way to exit a program or process.

    Best regards
    "A morning w/o coffee is like something w/o something else"


    Voyager 12.04 Xubuntu based on AMD Phenom Quad Core & Fedora on Sony Vaio


  7. #7
    Join Date
    Mar 2012
    Location
    Russia
    Beans
    104
    Distro
    Ubuntu 11.10 Oneiric Ocelot

    Re: Using bash to conditionally stop an application.

    For continue process after SIGSTOP, i think, use fg, because SIGCONT - run for daemon's only.

    http://www.real-world-systems.com/docs/bashref_6.html
    Last edited by CynicRus; March 16th, 2012 at 06:11 AM.

  8. #8
    Join Date
    Jul 2007
    Location
    Poland
    Beans
    4,158
    Distro
    Ubuntu 10.04 Lucid Lynx

    Re: Using bash to conditionally stop an application.

    i mentioned pgrep, but pkill accepts the same parameters (there are quite a few) and does the job directly
    http://linux.die.net/man/1/pkill

  9. #9
    Join Date
    Jan 2008
    Beans
    53

    Re: Using bash to conditionally stop an application.

    Update:
    Thank you all very much for your input and your help. Giving the second script the PID number instead of the program name seems to allow it to continue to what looks like a completion.

    Only two problems left.

    1.) The VPN dependant program gives an "unable to load an environment variable" error when it starts, and it isn't making any connections so I'll need to test that further before I can continue finish bug testing the scripts.

    2.) When I disconnected the VPN to test the scripts nothing seemed to happen. The second script brings me back to the command prompt ok, but it doesn't appear to stop the VPN dependant program.

    If I am unable to solve #2 above I will come back and give more information about it and ask some follow up questions. I just want to give myself a chance to figure this out first. Thank you all again for your help so far.

  10. #10
    Join Date
    Jan 2008
    Beans
    53

    Re: Using bash to conditionally stop an application.

    [Update:]
    Ok the environment variable issue wasn't affecting things, and the other problem came from a syntax error in the code that was found and fixed.

    In short the two scripts appear to be working well now with one minor annoyance.

    Problem:
    I would like to combine these two scripts into one script, but the problem is that starting a program inside a script causes the script to wait until the program finishes before the script can continue.

    The annoyance:
    I'm dealing with this problem by manually pressing CTRL+Z once to stop the VPN dependant program so the second script can take over starting and stopping it depending on the VPN connection status which it also takes control of.

    Questions:
    1.) Is there a way to start a program in -SIGSTOP mode? Or is there some other way around the problem described above? For example, would something like the following work to fork the process such as:
    Code:
    ...previous part of script...
    myprogram01 &
    ...script continues due to the "&"...
    2.) If this works then will the -SIGSTOP and -SIGCONT still work even though myprogram01 would be running in the background or would I have to bring it to the forground first with fg? Seems like all of this is getting a bit excessive.
    3.) Is there maybe something more simple I could do using the watch command in conjunction with cron?


    Note: For reference, this is the single script version of the two scripts I've been working on so far.
    It hasn't been tested yet due to the CTRL+Z issue described above.
    Code:
    #!/bin/bash
    #This is part one of a two part script to secure VPN dependant traffic after a disconnect from the VPN.
    
    #Attmept an initial connection until connected
    while :		#Executed as long as condition is true and/or, up to a disaster-condition if any.
    do
      connected=`nmcli -t -f VPN con status |grep yes`      #Store the current state of the VPN connection.
    	if [ $connected = "yes" ]; then
    		echo VPN connection activated.
    		break
    	else
      	echo Attempting VPN connection.       	   
      	nmcli -p con up uuid 07d345f0-3cb4-4b59-ba2b-7fdf9717e50a		#Retry the VPN 
      fi
    done
    
    myprogram01	#This is where I would have to press CTRL+Z to continue the script.
    program=`pidof myprogram01`
    
    #Monitor the connection.
    while true; do
    	vpnstring=$(nmcli -t -f VPN con status|grep -c yes)		#Define a string to test, 0 = no connection, 1 = connected.
    	date
    
    	case $vpnstring in				#Test a string.
    		"0")
    
    		echo "VPN disconnected"
    		kill -SIGSTOP $program		#Connection lost stop the VPN dependancy.
    
    		while :		#The connection has been lost, try to reconnect then break out once connected.
    			do
      			connected=`nmcli -t -f VPN con status |grep yes`      #Store the current state of the VPN connection.
    				if [ $connected = "yes" ]; then
    					echo VPN connection activated.
    					break
    				else
    			  	echo Attempting VPN connection.       	   
    			  	nmcli -p con up uuid 07d345f0-3cb4-4b59-ba2b-7fdf9717e50a		#Retry the VPN 
    			  fi
    		done
    	;;
    
    		"1")
    		echo "VPN connection active" 
    		kill -SIGCONT $program
    	;;
    	esac
    
    sleep 5
    done
    Thanks again for your patients and time.
    Last edited by landstander; March 17th, 2012 at 01:24 AM. Reason: clarifying some grammer.

Page 1 of 3 123 LastLast

Bookmarks

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •