I am writing a set of scripts that I want to be portable, but I need to know whether sh
on the current platform stands for bash
, ksh
, or ash
. Is there a clear way to do it?
What comes to my mind first is to inspect which shell has which --version
:
$ zsh --version
zsh 5.0.2 (x86_64-apple-darwin13.0)
$ bash --version
GNU bash, version 4.3.39(1)-release (x86_64-apple-darwin13.4.0)
Copyright (C) 2013 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
This is free software; you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.
$ ksh --version
version sh (AT&T Research) 93u+ 2012-08-01
$ dash --version
dash: 0: Illegal option --
$ pdksh --version
pdksh: pdksh: --: unknown option
Apart from being clumsy, this doesn't even produce results in all cases.
Edit
I need it for my bashrc/zshrc/...-like project, where I assign my current working shell to a variable, and use that variable everywhere.
I can't post my code because I need to solve the problem to enable overall cleanliness of my work. Moreover, it would be too much monkeycode... don't misunderstand it, but POSIX compatibility is too narrow to make my project small enough. I'd need to crutch on system configs otherwise.
However, I can post my UNIX Shell defining function:
PROJ_GET_SHELL () {
local PROJ_SHELL="`ps -p $$ | tail -1 | tr ' ' '\n' | tail -1`"
PROJ_local=(pdksh bash dash mksh zsh ksh sh)
for i in ${PROJ_local[*]}
do
if ! [ -z `echo $PROJ_SHELL | grep $i` ]
then
echo "$i"
break
fi
done
}
PS. The least bit of research shows that $SHELL doesn't change when running a shell as subprocess.
ksh
throws segfault whenzsh
andbash
don't. – theoden8 Jul 19 '15 at 17:51ksh
? Sounds like a bug inksh
but it also sounds like the way to portability is to be more conservative with your workload or use something other than the shell as a programming language if the task is complex and not really suited for a shell script. – Celada Jul 19 '15 at 17:54perl
, but writingzsh
scripts compatible withdash
is not a good idea. Moreover, they have different environmental variables, and working in general with all shells would be too much headache when you can make if-elses in a separate func. EDITED – theoden8 Jul 19 '15 at 17:58zsh
scripts compatible withdash
is not a good idea"? I happen to think that writing portable shell scripts is a good idea! (In which case they're not calledzsh
scripts ordash
scripts butsh
scripts.) I also don't understand your comment about generating shell scripts usingperl
— you are talking about autogenerated code here? – Celada Jul 19 '15 at 18:05sh
is pointing to then what's wrong withreadlink -f "$(command -v sh)"
? – jimmij Jul 19 '15 at 18:56bin/sh
might not be a symlink. – Celada Jul 19 '15 at 19:47sh
is. just use syntax which will work with any of them. – mikeserv Jul 19 '15 at 19:48ash
. For instance,alias .="$FILEMANAGER ." overrides
sourcein
ksh, or I can't use lists the same way in
zshand
ash`. There's a lot of such things that I don't have time to track. The most important reason is that I use my own method of defining what shell is i'm using to source the script and I crutch on it in all other files. – theoden8 Jul 19 '15 at 20:29yash
/dash
. That's why I keep improving it. – theoden8 Jul 19 '15 at 20:37