When I use the type command to find out if cat is a shell built-in or an external program I get the output below:

-$ type cat
cat is hashed (/bin/cat)

Does this mean that cat is an external program which is /bin/cat?

I got confused, because when I checked the output below for echo I got to see that it is a built-in but also a program /bin/echo

-$ type echo
echo is a shell builtin
-$ which echo

So I could not use the logic that /bin/cat necessarily means an external program, because echo was /bin/echo but still a built-in.

So how do I know what cat is? Built-in or external?

  • 1
    -The command cat is an external program that makes part of the system, per cause the many actions that it can perform is not a simple built-in. Jun 10, 2015 at 3:30
  • 12
    type which could give you the answer why which won't give you the answer.
    – Dubu
    Jun 10, 2015 at 13:46
  • 1
    Depends on the shell you are using
    – nsn
    Jun 10, 2015 at 17:28
  • 6
    Fun fact: both cat and ls are/were written by Stallman himself. You'd be surprised how much stuff he wrote. Don't forget he wrote the first versions of the compiler that is today the best compiler in the world that compiles EVERYTHING and most of the core utils. Just sayin'
    – Alec Teal
    Jun 11, 2015 at 14:12
  • 2
    @AlecTeal You do realize that most Unix systems use versions of ls and cat that long predate the GNU versions that Richard Stallman had a hand in?
    – Ross Ridge
    Jun 11, 2015 at 16:06

6 Answers 6


type tells you what the shell would use. For example:

$ type echo
echo is a shell builtin
$ type /bin/echo
/bin/echo is /bin/echo

That means that if, at the bash prompt, you type echo, you will get the built-in. If you specify the path, as in /bin/echo, you will get the external command.

which, by contrast is an external program that has no special knowledge of what the shell will do. On debian-like systems, which is a shell script which searches the PATH for the executable. Thus, it will give you the name of the external executable even if the shell would use a built-in.

If a command is only available as a built-in, which will return nothing:

$ type help
help is a shell builtin
$ which help

Now, let;s look at cat:

$ type cat
cat is hashed (/bin/cat)
$ which cat

cat is an external executable, not a shell builtin.

  • 5
    You could type -all echo to find out (in order) which are the different "echo" known to the shell (the first one being the one the shell will call, if you don't specify something to change the order, like invoking "echo" or \echo, or command echo ) Jun 10, 2015 at 9:28
  • Good answer. One addition: There are two versions of echo for historical reasons. It started out as an external command, then was added as a built-in. Early versions of the Bourne shell (/bin/sh) did not have it. /bin/echo was kept on for compatibility, since all sorts of things depended on it. (The same thing happened with test.)
    – alexis
    Jun 11, 2015 at 11:26
  • 1
    Side note: which itself can be a shell built-in cmd, for example in tcsh: which which which: shell built-in command. Jun 11, 2015 at 16:47
  • I'm arriving late to the party, but why don't you check its man page and you can actually see the number between parenthesis, which indicates if it is a shell built-in or whatever
    – poz2k4444
    Jun 16, 2015 at 20:34

cat is hashed (/bin/cat) is just like cat is /bin/cat (that is, it's an external program).

The difference is that you already ran cat in this session, so bash has already looked it up in $PATH and stored the resulting location in a hash table so it doesn't have to look it up again in this session.

To see all the commands that have been hashed in your session, run hash

$ hash
hits    command
   2    /usr/bin/sleep
   3    /usr/bin/man

$ type sleep
sleep is hashed (/usr/bin/sleep)

$ type man
man is hashed (/usr/bin/man)

$ type ls
ls is /usr/bin/ls

$ type cat
cat is /usr/bin/cat

$ type echo
echo is a shell builtin
  • 9
    Actually, in my opinion this is the only answer that addresses your question :) Jun 10, 2015 at 6:14
  • IMHO this ^^^ is true. This answer should be the accepted one. Feb 9, 2018 at 12:52

Another way to check list of shell builtin : Using compgen which is shell builtin itself!

Following command lists all shell builtin commands:

compgen -b

You can check for cat, echo by greping like:-

$ compgen -b | grep echo
$ compgen -b | grep cat

You can see compgen -b | grep cat returns with no output, means cat is not shell builtin.

Visit a list of useful options provided by compgen.

You can also use one another builtin command : help to display shell-builtin.

$ help help
help: help [-dms] [pattern ...]
    Display information about builtin commands.
  • I can't find any formal documentation for these options, do you know where it exists?
    – Random832
    Jun 10, 2015 at 14:21
  • @Random832 are you talking about options for compgen?
    – Pandya
    Jun 11, 2015 at 3:40
  • yeah, I couldn't find anything in the Bash manpage about what -b or half the other options mean. Found it later at gnu.org/software/bash/manual/html_node/…
    – Random832
    Jun 11, 2015 at 3:42
  • @Random832 try man bash | grep -e '-A action$' -A 32 you probably get output like this. (increase/decrease digit after -A to manage properly).
    – Pandya
    Jun 11, 2015 at 4:03

You can also use the command whereis that is more efficient because it shows where the command is on the machine like also the manual pages library, etc..

  • -Excuse me for my bad English, because I just learning yet and not so good using!... Jun 10, 2015 at 15:00

Others have already answered about cat, I would just like to explain the issue with echo. If you use type's -a option (list all matches), you will see that echo is both a shell builtin and an external program:

$ type -a echo
echo is a shell builtin
echo is /bin/echo

The two are completely independent of one another. type with no options will simply return the first matching command found. So, type foo will show you what will be executed if you run foo. There may be other options, but those won't be shown unless you use -a.


Since there are several good answers here about using type to find out if a command such as cat is a builtin or an external program. I am going to take a more general approach. There are some commands that must be builtins because they affect the current shell. Three classic examples are cd, exec, and exit. There are some commands that must not be builtins because their functionality depends on the behavior of the execve or system calls. Examples of such programs include su, sudo, calife and super. All other commands can be built as builtins or external programs. cat is a great example program of this class as there are shells that include it as a builtin and shells that do not. It is worth noting that many commands of this class that are available as builtins are also available as external programs.

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .