Take the 2-minute tour ×
Unix & Linux Stack Exchange is a question and answer site for users of Linux, FreeBSD and other Un*x-like operating systems.. It's 100% free, no registration required.

I am having an issue with the WINCH signal in the following code which is from a tutorial located at developerWorks®:

#!/bin/bash
trap 'get_window_size' WINCH                    # trap when a user has resized the window

_UNDERLINE_ON=`tput smul`                       # turn on underline
_UNDERLINE_OFF=`tput rmul`                      # turn off underline

get_window_size() {
  _WINDOW_X=`tput lines`
  _WINDOW_Y=`tput cols`

  _FULL_SPACES=`echo ""|awk '
  {
    _SPACES = '${_WINDOW_Y}'
    while (_SPACES-- > 0) printf (" ")
  }'`
  _FULL_UNDERLINE=`echo "${_UNDERLINE_ON}${_FULL_SPACES}${_UNDERLINE_OFF}"`

  unset _FULL_SPACES
  show_menu

  return 0
}

set_color() {
  tput clear
  PS3="Enter Selection[1-9]:"
  select _COLOR in "Black" "Blue" "Green" "Cyan" "Red" "Magenta" "Yellow" "White" "Exit"
  do
    case ${REPLY} in
       [1-8])  _X=`expr ${REPLY} - 1`;;
           9)  break;;
           *)  echo "Invalid Color"; continue;;
    esac

    if [[ ${1} = "b" ]]
    then
      tput setb ${_X}
        else
      tput setf ${_X}
    fi
  done
}

show_menu() {
  while [[ -z ${_ANS} ]]
  do
    tput civis
    tput clear

    cat <<- EOF
Window Size: ${_WINDOW_X} / ${_WINDOW_Y}


Select => ${_UNDERLINE_ON}     ${_UNDERLINE_OFF}

${_FULL_UNDERLINE}
B) Background Text Color
F) Foreground Text Color

X) Exit
EOF

    tput rc
    tput smul
    tput cnorm

    read _ANS
    tput rmul

    case ${_ANS} in
      [Bb])  set_color "b";;
      [Ff])  set_color "f";;
      [Xx])  tput clear; exit;;
         *)
             echo -e "Invalid Selection: ${_ANS}\c"
             sleep 2
             ;;
    esac
    unset _ANS
  done
}

tput sgr0
tput civis
tput clear
tput cup 3 10
tput sc
tput cup 0 0

[[ -n ${_ANS} ]] && unset _ANS
get_window_size

exit 0

Since I am trapping the WINCH (window change) signal, I expect that (each time I adjust the window which contains this running script) the get_window_size function will be invoked.

However, on my machine, it only traps the WINCH signal once (under specific conditions). The trap happens only if I use the xterm (in this case, gnome-terminal) Terminal menu to choose one of the default sizes (80x24, 80x43, 132x24, 132x43); further, it happens only the first such time. If I subsequently change the window size (using the Terminal menu item), no trapping occurs.

Also, if I don't use the Terminal menu item, but re-size using a pointing device, even the first trap does not happen.

Can someone help me to understand what is wrong (either with the code or with my expectation)?

share|improve this question

1 Answer 1

up vote 3 down vote accepted

I suspect there's something goofy in the way the script waits for a user action and/or a signal. Note that get_window_size calls show_menu, which is what waits for user input (read _ANS).

The trap command also causes get_window_size to be called by the SIGWINCH. I don't know if shell functions are re-entrant or not.

My expectations of how SIGWINCH should get generated, and when the trap function should get executed are basically the same as yours. I cut down the example script a bit, and made it non-reentrant. See below.

You may also want to consider trying your script with a different window manager. I used the venerable, speedy and highly configurable twm in my experiment.

#!/bin/bash
trap 'get_window_size' WINCH                    # trap when a user has resized the window
get_window_size() {
        _WINDOW_X=`tput lines`
        _WINDOW_Y=`tput cols`

        echo "X: $_WINDOW_X"
        echo "Y: $_WINDOW_Y"

        return 0
}

while read ALINE
do
        echo "Read: '$ALINE'"
done
share|improve this answer
    
Essentially, you were on to something in raising the re-entrancy question. I removed the call to show_menu from the get_window_size function and simply placed a call to show_menu beneath the call to get_window_size in the main section. This, indeed, resolves the issue! Thank you for your input! –  TheGeeko61 Jan 11 '12 at 6:01

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.