tags:

views:

68

answers:

3

Sorry if this is better suited at serverfault, but I think it learns more towards the programming side of things.

I have some code that's going into /etc/rc.local to detect what type of touch screen monitor is plugged in and changes out the xorg.conf before launching X. Here is a small snippet:

CURRENT_MONITOR=`ls /dev/usb | grep 'egalax_touch\|quanta_touch'`
case $CURRENT_MONITOR in
'')
    CURRENT_MONITOR='none'
    ;;
esac

If one of those two touch screens is plugged in, it works just fine. If any other monitor is plugged in, it stops at the "CURRENT_MONITOR=ls /dev/usb | grep 'egalax_touch\|quanta_touch'."

For testing I touched two files. One before creating CURRENT_MONITOR and one after CURRENT_MONITOR and only file touched before is created.

I'm not a bash programmer so this might be something very obvious.

+2  A: 

Edit: the answer below was not actually correct. The correct solution is in the comments: the script included set -e, so a failing command would terminate the script, and in the case where neither monitor was plugged in the grep would fail.


If CURRENT_MONITOR contains spaces, then your case statement will become (say)

case monitor1 monitor2 in

which is a syntax error. You need to quote the variable:

case "$CURRENT_MONITOR" in
'')
    CURRENT_MONITOR='none'
    ;;
esac
Andy Mortimer
While quoting is a good idea it seems; it's still failing before it even makes it to that case statement.
Kyle Terry
Sorry, I mis-read; if it's not even getting to the case statement, then quoting won't help you.Perhaps using `exec 2>/path/to/file` and then `set -x`, as jschmier writes, will help you track down the problem.It does seem strange though.A thought: you don't by any any chance have `set -e` in effect, do you? That'll make the script exit on the first failure, and if you don't have any of those monitors plugged in, the grep will fail.
Andy Mortimer
It turns out it was -e doing it and the grep failing. I know what I need to do now! Thanks so much.
Kyle Terry
Thanks to jschmier too!
Kyle Terry
A: 
CURRENT_MONITOR=`ls /dev/usb | grep 'egalax_touch\|quanta_touch'` 
echo $CURRENT_MONITOR | od -xa > some_file
# This will let you see what is in the var that is failing, even if it has funky bytes in it.
# some_file could be /dev/console or you could pipe it into logger or you could use tee and do both
case $CURRENT_MONITOR in 
'') 
    CURRENT_MONITOR='none' 
    ;; 
esac 
nategoose
+1  A: 

I believe quoting the variable will fix your problem:

case "$CURRENT_MONITOR" in

if the directory is empty, without the quotes that statement evaluates to:

case in

which is a syntax error and will cause your script to abort. Are you capturing stderr somewhere. If so, it's likely you'll see:

bash: syntax error near unexpected token `'''

Also, you should avoid parsing ls:

for i in /dev/usb/*
do
    case i in
        *egalax_touch*)
...

However, you don't show your complete case statement. If that's all you're doing with it, then why not:

if [[ -z $CURRENT_MONITOR ]]; then $CURRENT_MONITOR='none'; fi

or

[[ ${CURRENT_MONITOR:=none} ]]        # assigns a default if null or unset

or

: ${CURRENT_MONITOR:=none}
Dennis Williamson
I love the for loop. Thanks for showing this to me!
Kyle Terry