2

I am looking for a very simple command to print the absolute path of ls. I have tried a lot of different methods and can't seem to find the correct answer. The code is meant to be along the line of cd; pwd If anyone could help me out I'd be very happy! Thank you!

A few of my unsuccessful attempts:

ls pwd
ls; pwd
ls $PWD
cd; ls pwd
Elina
  • 37
  • 2
  • 1
    Does this answer your question? [How to find directory of some command?](https://stackoverflow.com/questions/2869100/how-to-find-directory-of-some-command) – pjh Aug 02 '23 at 23:48
  • Note that Stack Overflow is only for questions about writing software. General UNIX tool questions are generally better suited to [unix.se] or [Super User](https://superuser.com/). – Charles Duffy Aug 02 '23 at 23:52
  • SInce there could several `ls` in your PATH, I would do a `type -a ls` to see all of them. This would also reveal if you have function or alias named `ls`, masking the `ls` executable. – user1934428 Aug 03 '23 at 07:03

1 Answers1

2

In Bash, run type -p ls. For example, on my system:

$ type -p ls
/bin/ls

If it has to work not only in Bash, but in any POSIX shell, run command -v ls:

$ command -v ls
/bin/ls

Alternatively, if command -v ... doesn't work, run this (without the leading $):

$ (U="$(type ls)"; U="${U#*/}/"; echo "${U%)}")
/bin/ls

All approaches above use the shell built-ins type or command. These builtins are available in Bash and many other similar shells. They don't need any other (external) command to be installed.

pts
  • 80,836
  • 20
  • 110
  • 183
  • 1
    `command -v` is guaranteed to be available across all POSIX shells; `type` is not. – Charles Duffy Aug 02 '23 at 23:52
  • @CharlesDuffy: Unfortunately, `busybox sh -c 'command -v ls'` on my system prints just `ls`, not `/bin/ls`. However, `busybox sh -c 'type ls'` doesn't print the full pathname either. – pts Aug 03 '23 at 00:02
  • @CharlesDuffy: Thank you for your comment, I've added `command -v ls` to my answer. – pts Aug 03 '23 at 00:06
  • Busybox is a special case because every executable that busybox provides (a set that includes `ls`!) is effectively a builtin there. You can delete `/bin/ls` on a host where you're using busybox sh, but `ls` will still work inside the busybox copy of sh (with the same behavior as you'd get from `busybox ls`) since it's coming from in-process. – Charles Duffy Aug 03 '23 at 01:13
  • Thanks for the help! I am able to make it work well like this, but also found a simple line that also gave me the correct pathway; 'which ls' – Elina Aug 03 '23 at 02:13
  • 2
    @Elina: `which` is an external command, which is not available on all systems. If it's available, then it works well for finding the absolute pathname of commands. – pts Aug 03 '23 at 09:23
  • 2
    @Elina, ...note in particular that `which` doesn't know about shell functions, aliases or builtins, so its output is sometimes wrong. (Consider the case above where in busybox `ls` _isn't_ `/bin/ls` but instead is a command built into busybox itself as an example; `which` will tell you that `/bin/ls` is used, but it's telling you something incorrect in that case: there's no `execve()` when starting busybox's built-in `ls` in busybox sh, so it doesn't start a new `/bin/` executable at all) – Charles Duffy Aug 03 '23 at 15:01