17

This question already has an answer here:

There is not much to explain here. Just want to know why echo $SHELL always gives the output /bin/bash even though I switch to other shells. What do I have to do to make sure the $SHELL gives the correct shell path that I am in.

[root@localhost user]# echo $0
bash
[root@localhost user]# echo $SHELL
/bin/bash
[root@localhost user]# csh
[root@localhost user]# echo $0
csh
[root@localhost user]# echo $SHELL
/bin/bash
[root@localhost user]# tcsh
[root@localhost user]# echo $0
tcsh
[root@localhost user]# echo $SHELL
/bin/bash
[root@localhost user]# sh
sh-4.2# echo $0
sh
sh-4.2# echo $SHELL
/bin/bash
sh-4.2# 
[root@localhost user]# which csh
/bin/csh
[root@localhost user]# which csh
/bin/csh

marked as duplicate by Michael Mrozek Dec 14 '16 at 17:00

This question has been asked before and already has an answer. If those answers do not fully address your question, please ask a new question.

34

$SHELL is the environment variable that holds your preferred shell, not the currently running shell. It's initialised by login or any other application that logs you in based on the shell field in your user entry in the passwd database (your login shell).

That variable is used to tell applications like xterm, vim... what shell they should start for you when they start a shell. You typically change it when you want to use another shell than the one set for you in the passwd database.

To get a path of the current shell interpreter, on Linux, and with Bourne or csh like shells, you can do:

readlink "/proc/$$/exe"

The rc equivalent:

readlink /proc/$pid/exe

The fish equivalent:

set pid %self
readlink /proc/$pid/exe

csh/tcsh set the $shell variable to the path of the shell.

In Bourne-like shells, $0 will contain the first argument that the shell received (argv[0]) which by convention is the name of the command being invoked (though login applications, again by convention make the first character a - to tell the shell it's a login shell and should for instance source the .profile or .login file containing your login session customisations) when not called to interpret a script or when called with shell -c '...' without extra arguments.

In:

$ bash -c 'echo "$0"'
bash
$ /bin/bash -c 'echo "$0"'
/bin/bash

It's my shell that calls /bin/bash in both cases, but in the first case with bash as its first argument, and in the second case with /bin/bash. Several shells allow passing arbitrary strings instead like:

$ (exec -a whatever bash -c 'echo "$0"')
whatever

In ksh/bash/zsh/yash.

  • 4
    Stéphane knows this of course, but for others, this is documented in POSIX Base Definitions section 8.3. – Stephen Kitt Dec 14 '16 at 8:09
  • 1
    This was really helpful. And it opened a new set of questions for me that were infact answered after going through POSIX base definitions section as mentioned by @StephenKitt. – Shashank Vyas Dec 14 '16 at 9:41
  • 1
    Your fish equivalent has the side effect of setting a variable. I suggest readlink /proc/(echo %self)/exe instead. – Max Ried Dec 14 '16 at 16:23
  • @StéphaneChazelas Are you sure it does? I straced fish -c "readlink /proc/1/exe" and fish -c "readlink /proc/(echo %self)/exe". Both only issue just one clone-syscall, neither forks nor execs. But I'm tired, maybe I'm missing something. – Max Ried Dec 15 '16 at 19:29
  • @Max looks like you're right. I thought ksh93 was the only shell to do this kind of optimisation (funnily enough, I was making the fish original author aware of those ksh93 optimisations just yesterday). Thanks for making me aware of it. – Stéphane Chazelas Dec 15 '16 at 20:42
2

If the output of echo $0 command is -bash it means that bash was invoked as a login shell. If the output is only bash, then you are in a non-login shell.

As the ENV is triggered to show the desired output it is giving you /bin/bash

[root@dcconnect ~]# env | grep -i SHELL
SHELL=/bin/bash

Out put of echo #SHELL is pulled from the ENV variable

0

The $0 is the command that started your shell. $SHELL is the default shell in your system

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