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.

Let's say I want to search for a string in a big file: grep foo bar.txt | less, but I actually type grep foobar.txt | less. Now, grep is waiting for me to type something on the terminal. It appears that the command is taking forever, until I notice my mistake.

Can the shell (any shell, or perhaps tmux) detect that a command is waiting for console input, and warn me?

Edit: It seems like each process has a standard input, and the shell has no way of knowing if it's actually waiting for something to arrive there. However, shells like zsh know the command line arguments for common commands like grep and could therefore warn me for the programs it knows.

(grep fTab does not try to complete anything, grep foo bTab will try to complete the filename.)

share|improve this question

2 Answers 2

up vote 2 down vote accepted

If you know you're never going to use grep to read from the terminal, you could redefine grep as:

grep() {
  if [ -t 0 ]; then
    < /dev/null command grep "$@"
  else
    command grep "$@"
  fi
}

That will not give you any warning about you typo. But at least it will return without a match immediately. It will also affect behaviour when - or /dev/stdin is passed as an argument to grep.

Edit:

Actually, a way to get a warning would be to close stdin instead of redirecting it from /dev/null:

grep() {
  if [ -t 0 ]; then
    <&- command grep "$@"
  else
    command grep "$@"
  fi
}

$ grep foobar.txt
grep: (standard input): Bad file descriptor
share|improve this answer

No, because the shell has no way to know whether the program is blocking on input. Even if it were, it can't know whether input will eventually come (see the halting problem). What if it's expecting input from the terminal? You could wait minutes, days, decades to give the input it's waiting for. less happens to block the input from getting to grep, but that's not always the case, e.g. try cat | grep foo - it will process what you type on the command line (Ctrl+D to finish).

share|improve this answer
1  
okay, poking around a bit with lsof it seems like there's no general way. However, shells like zsh know the command line arguments for grep and thus could detect if a file argument is missing. –  Michael Kuhn Feb 5 '13 at 15:28
2  
zsh's completion function for grep knows the arguments it expects, but I doubt it's built into the shell per se. Either way, how would it know whether you intend to type/copy the text to stdin yourself? –  Kevin Feb 5 '13 at 15:43
    
I'd like it to warn me, not throw an error. In the rare circumstance where I want to paste something in, the warning doesn't harm. –  Michael Kuhn Feb 5 '13 at 16:38
    
You'd like it to warn you based on what conditions? If you can enumerate concrete conditions, you can wrap it in a function as stephane suggests, otherwise neither the shell nor grep can read your mind. –  Kevin Feb 5 '13 at 16:54
    
The issue isn't one of solving the halting problem. Conceptually, there would be nothing preventing the "read character from terminal" code from using some method of out-of-band signalling to notify the terminal when it's waiting and when it's at least temporarily sated. Doing that might require patching multiple places in the OS, but it would be both possible and useful (I'm not sure whether it would be useful enough to justify the effort, but it would certainly seem reasonable). –  supercat Apr 25 at 19:33

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.