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.

What is the purpose of the sh command when used interactively and when used inside of a bash script?

Other than on the hash bang line (the first line) should sh ever be replaced with bash on a bash system?

Example:

#!/bin/bash
sh -c "command"
share|improve this question
3  
Please, only 1 question per question :P –  Oliver Salzburg Apr 5 '12 at 13:36
1  
possible duplicate of What is the difference between bash and sh –  Oliver Salzburg Apr 5 '12 at 13:37
1  
It's not a duplicate because the question would apply equally to any similar shell command. –  broiyan Apr 5 '12 at 13:38
add comment

5 Answers

up vote 11 down vote accepted

So many questions... I'll take them one at a time.

1) What is the purpose of the sh command when used interactively? Provides a new environment context, so if you wanted to experiment with some environment variable setting, you could. And when you were done, exit out and no harm done.

Also, if you were in a different shell like zsh or csh, and wanted to execute in a sh shell, this would switch you.

2) When used in a bash script like you have above, it will again provide a contained environment context for "command" to run in. You can also use it with the

#!/bin/bash
sh -c "command" &
and fork off "command" to run in parallel with the rest of your script.

3) I would say, if it is something that specifically needs bash, then explicitly put it in your hash bang line. But since on most later *nix systems sh is equivalent to bash, it is probably not necessary.

share|improve this answer
    
I think your #3 answers the question: "Is #!/bin/bash necessary on later systems?" and your answer is no. As to whether bash is necessary instead of sh I think you are implying that the answer is only if you specifically need bash. –  broiyan Apr 5 '12 at 13:51
1  
"Most later" does not include Debian and its derivatives since they use Dash as /bin/sh, so it's quite a large proportion of systems where this isn't true. –  Daniel Andersson Apr 5 '12 at 14:27
1  
As for your answer "2)": one could do this without the sh -c construct by just appending & to the command directly. –  Daniel Andersson Apr 5 '12 at 14:29
1  
Well, the fork off to run in parallel, yes. To be running it in an independent environment, no. –  pottsdl Apr 5 '12 at 14:31
1  
@pottsdl: [comment -2]: yes, but the sh -c part does not add to the possibility to run in parallel, as you said as well in your comment, so in my eyes it was unnecessary to mention. It's not wrong, but it's not related to the question in itself, imho. –  Daniel Andersson Apr 5 '12 at 14:38
show 1 more comment

What happens when I execute sh?

If you simply start sh on the shell, you'll start another shell inside your current shell.

What happens when I use sh in a script?

The same thing, you start another shell inside the shell that is processing the script.

Should I simply use /bin/bash if that's what /bin/sh points to anyway?

No. If the script was designed to work with any shell, then it is designed to work against the lowest common denominator between all shells (to my understanding, this is part of the POSIX standard).
Changing to a specific interpreter shouldn't be harmful (because, all of them comply to the same standard) but it reduces compatibility while providing no benefit at all.

So, I should always use /bin/sh then?

As an interpreter

No. If you're writing a script yourself, then you can also use a more specific interpreter (like bash) if that interpreter provides additional features you want to make use of. But keep in mind that everyone who uses your script will be required to have your chosen interpreter.

To start another process

If you simply want to start a new process in its own context, then, by all means, use /bin/sh.

So what's the point of it all?

If you want to execute something in its own context, you should execute it in a new shell.
The easiest way to achieve that is to start a new shell (using sh) and passing the command to it.

As long as your something isn't a script specifically crafted for a specific shell, there is no reason to invoke a specific shell. Just invoke any shell, by using sh.

If you have a script, that uses special syntax only available in bash, then you should set the shebang accordingly.

share|improve this answer
2  
Even if bash and sh are the same program are the same on your system, bash should work more like sh than bash if invoked with that name. Scripts using sh semantics are more portable than scripts using bash extensions. –  BillThor Apr 6 '12 at 4:07
add comment

sh is not a shell command but a program you are calling. Your line will search for sh in your path. In most cases it will just execute /bin/sh which is in the path.

This will start a new process.

/bin/sh is not guaranteed to be bash, it is now on many systems bash but on several Unix system it is the Bourne shell. If you execute /bin/sh you can just expect a shell adhering to the POSIX standard.

share|improve this answer
    
And the purpose is... ? –  broiyan Apr 5 '12 at 13:42
    
In your example to start a shell (not mandatorily bash) with the command as an argument. It will execute as a different process (different memory space, possibility to detach it, ...) –  Matteo Apr 5 '12 at 13:45
add comment

Why /bin/sh ??

As others have pointed out you get to decide what that actually means :) (Or your distro does for you.)

For bash at least it has a particular meaning...

From the bash man page:

" If bash is invoked with the name sh, it tries to mimic the startup behavior of historical versions of sh as closely as possible, while conforming to the POSIX standard as well. "

So if you /bin/sh points to /bin/bash then you get that behaviour.

#!/bin/bash

gives you "standard" bash (and its "bashisms")

of course /bin/sh may actually be a link to say /bin/dash or ksh or some other "shell".

The bash man page is huge but this particular info is only...145 lines in :)

There are a couple of good introductions about: The Advanced Bash Scripting Guide is excellent.

http://tldp.org/LDP/abs/html/

If your on Debian / Ubuntu (or other derivatives) :

abs-guide - The Advanced Bash-Scripting Guide

debian-reference-en -> Debian system administration guide, English original

e.g.

apt-get install abs-guide

FYI dash: (edited down to description)

$ apt-cache show dash

says:

Description-en: POSIX-compliant shell The Debian Almquist Shell

(dash) is a POSIX-compliant shell derived from ash. .

Since it executes scripts faster than bash,

and has fewer library dependencies

(making it more robust against software or hardware failures),

it is used as the default system shell on Debian systems.

Homepage:

http://gondor.apana.org.au/~herbert/dash/

share|improve this answer
add comment

1) It's a shell. Its purpose in interactive mode is to read input from user and execute specified commands. In non-interactive mode it reads all commands from script file, so it works without user ever touching the keyboard.

2) The difference between "sh -c command" and just "command" in script file is that in the former case command is forked from separate shell process, whereas in the latter case it is forked from the process running main shell script (i.e. has access to its file descriptors, environment etc.). So we have additional process in the process tree in the former case, and also some degree of isolation.

3) /bin/sh may be symlink to /bin/zsh (for example), so, yes, if you mean to run bash child script from the bash main script you should explicitly say "bash -c". If child script is shell-independent, then "sh -c" will do as well.

share|improve this answer
add comment

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.