2

I frequently use screen when I log into the interactive nodes to a supercomputer that I have access to -- and I often run things and move on. There are about 20 separate nodes that I can log into; and if I check any one of them I'll have something like 4 detached sessions. Each of those sessions will have maybe 5 screen sessions within that.

Is there a quick way to cycle through all of these and close them down if they are not running any processes? My current process is to screen -ls and then screen -r #### then type exit until I'm back to the base screen.

EDIT

Here's a script that I based on Thor's answer:

for screen_pid in $(screen -ls | sed -nr 's/^\t+([0-9]+).*/\1/p');
do 
  for shell_tty in $(ps h --ppid $screen_pid -o tty);
  do
    number_of_processes=$(ps a -o tty | grep $shell_tty | wc -l)
    if (( number_of_processes > 1 )); then 
      echo number $number_of_processes
    else
      # screen -S $screen_pid -X kill  
      screen -S $screen_pid -X quit
    fi
  done
done

When I run it with kill, nothing seems to happen to the sessions. When I run with quit, it appears to kill the whole session and anything running inside (without checking if there are processes running). Tweaks from here?

1
  • 1
    Using Ctrl-d to exit would speed you up.
    – Thor
    Sep 30, 2012 at 8:08

1 Answer 1

2

One option is to run the programs as the screen primary command, then screen will exit when they are done.

If the above is not useful, you could estimate how many processes are running by looking at how many are connected to the shells tty.

A couple of idioms are needed

Extract screen pid from screen -ls:

screen -ls | sed -nr 's/^\t+([0-9]+).*/\1/p'

Lookup who has that pid as parent:

ps h --ppid $screen_pid -o tty

See how many processes are connected to that tty:

ps a -o tty | grep $shell_tty | wc -l

Putting it all together

screen -ls | sed -nr 's/^\t+([0-9]+).*/\1/p' | while read screen_pid; do
  shell_tty=$(ps h --ppid $screen_pid -o tty)
  number_of_processes=$(ps a -o tty | grep $shell_tty | wc -l)
  if (( number_of_processes > 1 )); then
    # more than the shell is running
  else
    # can be killed
  fi
done
1
  • I've modified it slightly so I could follow what was happening in your script a bit. I put it in the question under EDIT because the formatting made it impossible here.
    – JBWhitmore
    Oct 1, 2012 at 8:21

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .