Take the 2-minute tour ×
Super User is a question and answer site for computer enthusiasts and power users. It's 100% free, no registration required.

I read here that this should work, but it doesn't:

# usage: wall [file]
root@sys:~> mesg
is y

root@sys:~> wall "who's out there"
wall: can't read who's out there.

If mesg is set to y, what's preventing me from broadcasting a string? Note, I did confirm that the file option works:

root@sys:~> wall test
Broadcast Message from root@sys (/dev/pts/1) at 15:23 ... 
Who's out there?
share|improve this question

1 Answer 1

up vote 12 down vote accepted

The problem lies in the syntax used in the linked article. To understand what exactly goes wrong, let's have a look at man wall:

Usage from man wall:

wall [file]

Wall displays the contents of file or, by default, its standard input

So wall accepts either of two sources for its message.

File name argument

Any command line argument given to wall has to be a file name. As there isn't a reliable way to tell if the argument is meant as message or file name, wall will assume it's the latter, ignore anything coming in on standard input, and try to read the message from that file.

In the given case, it tries to read from the file who's out there and does not find it. Note that reading from a file is usually restricted to the superuser. If you'd executed wall "who's out there" as an unprivileged user, likely its output would have been, wall: will not read who's out there - use stdin.

Standard input

If it doesn't get a file name argument on its command line, it will start reading from standard input. There are several ways to feed information to the standard input of a command. One is to use a UNIX pipe. A pipeline will connect the standard output of its lefthand-side command to the standard input of its righthand-side command:

$ echo "who's out there" | wall

Another way is to use a here document. A here document is a shell construct that passes a string (up to a specified end marker on a line of its own) directly to the standard input of a command, without the intermediate step of having a distinct command produce that output:

$ wall << .
who's out there?
.

This would be a "useless use of here documents", because by default the terminal itself will be connected to wall's standard input and wall will start reading from it until it receives an end-of-file character (Ctrl+D):

$ wall
who's out there?
^D

As Rich Homolka noted in the comments, some shells support here strings which allow passing a literal string without command or end markers:

$ wall <<< "who's out there?"

All feed something to wall's standard input. The difference is that a pipeline connects the output of another command to it, while here documents and here strings pass the string directly. The latter two's advantage here is an aesthetic one, as the echo command from the pipe example is a shell built-in command, so it will be the shell providing wall's input in all cases.

share|improve this answer
1  
Bash/zsh has another format to avoid the echo xxx | yyy syntax, which I find cludgy wall <<<'your message' –  Rich Homolka Jun 15 '11 at 16:20
    
I'm not sure about that one Rich - the syntax of wall shouldn't be based off the shell unless there's a .bashrc or whatever the zsh equivalent is. I use bash too. –  mjb Jun 17 '11 at 12:45
    
Thank you peth - that's the syntactical organization I needed to learn! –  mjb Jun 17 '11 at 12:46
    
My mistake Rich! With Peth's clarification I now see that you were offering the wall <<< string sintax. That's pretty great. Can either of you explain what <<< is doing exactly (and why it would be more efficient as peth said)? I find it odd that a cmd that requires a file can accept a string after <<<. Thanks again. –  mjb Jun 17 '11 at 21:12
    
Really useful :) thanks. –  Patryk Feb 10 '12 at 19:31

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.