Listing Files in a Directory
Now that you are able to move from one directory to another, you will want to start displaying the contents of these directories. The
ls
command (ls
is short for list) can be used to display the contents of a directory as well as detailed information about the files that are within a directory.
By itself, the
ls
command will list the files in the current directory:sysadmin@localhost:~$ lsDesktop Documents Downloads Music Pictures Public TemplatesVideossysadmin@localhost:~$
1 Listing Colors
There are many different types of files in Linux. As you learn more about Linux, you will discover many of these types. The following is a brief summary of some of the more common file types:
Type | Description |
---|---|
plain file | A file that isn't a special file type; also called a normal file |
directory | A directory file (contains other files) |
executable | A file that can be run like a program |
symbolic link | A file that points to another file |
On many Linux distributions, regular user accounts are modified so that the
ls
command displays filenames, color-coded by file type. For example, directories may be displayed in blue, executable files may be displayed in green, and symbolic links may be displayed in cyan (light blue).
This is not a normal behavior for the
ls
command, but rather something that happens when you use the --color
option to the ls
command. The reason why ls
seems to automatically perform this coloring, is that there is an alias for the ls
command so it runs with the --color
option:sysadmin@localhost:~$ aliasalias egrep='egrep --color=auto'alias fgrep='fgrep --color=auto'alias l='ls -CF'alias grep='grep --color=auto'alias ls='ls --color=auto'alias la='ls -A' alias ll='ls -alF'sysadmin@localhost:~$
As you can see from the output above, when the
ls
command is executed, it really runs the command ls --color=auto
.
In some cases, you might not want to see all of the colors (they can be a bit distracting sometimes). To avoid using the alias, place a backslash character
\
in front of your command:sysadmin@localhost:~$ lsDesktop Documents Downloads Music Pictures Public TemplatesVideossysadmin@localhost:~$ \lsDesktop Documents Downloads Music Pictures Public TemplatesVideossysadmin@localhost:~$
2 Listing Hidden Files
When you use the
ls
command to display the contents of a directory, not all files are shown automatically. The ls
command doesn't display hidden files by default. A hidden file is any file (or directory) that begins with a dot .
character.
To display all files, including hidden files, use the
-a
option to the ls
command:sysadmin@localhost:~$ ls -a. .bashrc .selected_editor Downloads Public.. .cache Desktop Music Templates.bash_logout .profile Documents Pictures Videos
Why are files hidden in the first place? Most of the hidden files are customization files, designed to customize how Linux, your shell or programs work. For example, the
.bashrc
file in your home directory customizes features of the shell, such as creating or modifying variables and aliases.
These customization files are not ones that you work with on a regular basis. There are also many of them, as you can see, and having them displayed will make it more difficult to find the files that you do regularly work with. So, the fact that they are hidden is to your benefit.
3 Long Display Listing
There is information about each file, called metadata that is sometimes helpful to display. This may include who owns a file, the size of a file and the last time the contents of a file were modified. You can display this information by using the
-l
option to the ls
command:sysadmin@localhost:~$ ls -ltotal 0drwxr-xr-x 1 sysadmin sysadmin 0 Jan 29 2015 Desktopdrwxr-xr-x 1 sysadmin sysadmin 0 Jan 29 2015 Documentsdrwxr-xr-x 1 sysadmin sysadmin 0 Jan 29 2015 Downloadsdrwxr-xr-x 1 sysadmin sysadmin 0 Jan 29 2015 Musicdrwxr-xr-x 1 sysadmin sysadmin 0 Jan 29 2015 Picturesdrwxr-xr-x 1 sysadmin sysadmin 0 Jan 29 2015 Publicdrwxr-xr-x 1 sysadmin sysadmin 0 Jan 29 2015 Templatesdrwxr-xr-x 1 sysadmin sysadmin 0 Jan 29 2015 Videossysadmin@localhost:~$
In the output above, each line describes metadata about a single file. The following describes each of the fields of data that you will see in the output of the
ls -l
command:3.1 Human Readable Sizes
When you display file sizes with the
-l
option to the ls
command, you end up with file sizes in bytes. For text files, a byte is 1 character.
For smaller files, byte sizes are fine. However, for larger files it is hard to comprehend how large the file is. For example, consider the output of the following command:
sysadmin@localhost:~$ ls -l /usr/bin/omshell-rwxr-xr-c 1 root root 1561400 Oct 9 2012 /usr/bin/omshellsysadmin@localhost:~$
As you can see, the file size is hard to determine in bytes. Is 1561400 a large file or small? It seems fairly large, but it is hard to determine using bytes.
Think of it this way: if someone were to give you the distance between Boston and New York using inches, that value would essentially be meaningless because for a distance like that, you think in terms of miles.
It would be better if the file size was presented in a more human readable size, like megabytes or gigabytes. To accomplish this, add the
-h
option to the ls
command:sysadmin@localhost:~$ ls -lh /usr/bin/omshell-rwxr-xr-c 1 root root 1.5M Oct 9 2012 /usr/bin/omshellsysadmin@localhost:~$
Important: The
-h
option must be used with the -l
option.4 Listing Directories
When the command
ls -d
is used, it refers to the current directory, and not the contents within it. Without any other options, it is rather meaningless, although it is important to note that the current directory is always referred to with a single period (.
):sysadmin@localhost:~$ ls -d.
To use the
ls -d
command in a meaningful way requires the addition of the -l
option. In this case, note that the first command lists the details of the contents in the /home/sysadmin
directory, while the second command lists the /home/sysadmin
directory itself.sysadmin@localhost:~$ ls -ltotal 0drwxr-xr-x 1 sysadmin sysadmin 0 Apr 15 2015 Desktopdrwxr-xr-x 1 sysadmin sysadmin 0 Apr 15 2015 Documentsdrwxr-xr-x 1 sysadmin sysadmin 0 Apr 15 2015 Downloadsdrwxr-xr-x 1 sysadmin sysadmin 0 Apr 15 2015 Musicdrwxr-xr-x 1 sysadmin sysadmin 0 Apr 15 2015 Picturesdrwxr-xr-x 1 sysadmin sysadmin 0 Apr 15 2015 Publicdrwxr-xr-x 1 sysadmin sysadmin 0 Apr 15 2015 Templatesdrwxr-xr-x 1 sysadmin sysadmin 0 Apr 15 2015 Videosdrwxr-xr-x 1 sysadmin sysadmin 420 Apr 15 2015 testsysadmin@localhost:~$ ls -lddrwxr-xr-x 1 sysadmin sysadmin 224 Nov 7 17:07 .sysadmin@localhost:~$
Note the single period at the end of the second long listing. This indicates that the current directory is being listed, and not the contents.
5 Recursive Listing
There will be times when you want to display all of the files in a directory as well as all of the files in all subdirectories under a directory. This is called a recursive listing.
To perform a recursive listing, use the
-R
option to the ls
command:
Note: The output shown below will vary from the results you will see if you execute the command within the virtual machine environment of this course.
sysadmin@localhost:~$ ls -R /etc/ppp/etc/ppp:chap-secrets ip-down.ipv6to4 ip-up.ipv6to4 ipv6-up pap-secretsip-down ip-up ipv6-down options peers/etc/ppp/peers:sysadmin@localhost:~$
Note that in the previous example, the files in the
/etc/ppp
directory were listed first. After that, the files in the /etc/ppp/peers
directory were listed (there were no files in this case, but if any file had been in this directory, they would have been displayed).
Be careful with this option; for example, running the command
ls -R /
would list every file on the file system, including all files on any attached USB device and DVD in the system. Limit the use of the -R
option to smaller directory structures.6 Sort a Listing
By default, the
ls
command sorts files alphabetically by file name. Sometimes, It may be useful to sort files using different criteria.
To sort files by size, we can use the
-S
option. Note the difference in the output of the following two commands:sysadmin@localhost:~$ ls /etc/sshmoduli ssh_host_dsa_key.pub ssh_host_rsa_key sshd_confissh_config ssh_host_ecdsa_key ssh_host_rsa_key.pubsysadmin@localhost:~$ ls -S /etc/sshssh_host_dsa_key ssh_host_ecdsa_key.pub ssh_import_id moduli ssh_host_dsa_key ssh_host_ecdsa_keysshd_config ssh_host_dsa_key.pub ssh_host_ecdsa_key.pubssh_host_rsa_key ssh_host_rsa_key.pubsysadmin@localhost:~$ssh_config ssh_import_id
The same files and directories are listed, but in a different order. While the
-S
option works by itself, you can't really tell that the output is sorted by size, so it is most useful when used with the -l
option. The following command will list files from largest to smallest and display the actual size of the file.sysadmin@localhost:~$ ls -lS /etc/sshtotal 160-rw-r--r-- 1 root root 125749 Apr 29 2014 moduli-rw-r--r-- 1 root root 2489 Jan 29 2015 sshd_config-rw-r--r-- 1 root root 1669 Apr 29 2014 ssh_config-rw------- 1 root root 1675 Jan 29 2015 ssh_host_rsa_key -rw------- 1 root root 668 Jan 29 2015 ssh_host_dsa_key-rw-r--r-- 1 root root 302 Jan 10 2011 ssh_import_id-rw-r--r-- 1 root root 607 Jan 29 2015 ssh_host_dsa_key.pub -rw-r--r-- 1 root root 399 Jan 29 2015 ssh_host_rsa_key.pub -rw------- 1 root root 227 Jan 29 2015 ssh_host_ecdsa_keysysadmin@localhost:~$-rw-r--r-- 1 root root 179 Jan 29 2015 ssh_host_ecdsa_key.pub
It may also be useful to use the
-h
option to display human-readable file sizes:sysadmin@localhost:~$ ls -lSh /etc/sshtotal 160K-rw-r--r-- 1 root root 123K Apr 29 2014 moduli-rw------- 1 root root 1.7K Jan 29 2015 ssh_host_rsa_key-rw-r--r-- 1 root root 2.5K Jan 29 2015 sshd_config -rw-r--r-- 1 root root 1.7K Apr 29 2014 ssh_config-rw-r--r-- 1 root root 399 Jan 29 2015 ssh_host_rsa_key.pub-rw------- 1 root root 668 Jan 29 2015 ssh_host_dsa_key -rw-r--r-- 1 root root 607 Jan 29 2015 ssh_host_dsa_key.pub -rw-r--r-- 1 root root 302 Jan 10 2011 ssh_import_idsysadmin@localhost:~$-rw------- 1 root root 227 Jan 29 2015 ssh_host_ecdsa_key-rw-r--r-- 1 root root 179 Jan 29 2015 ssh_host_ecdsa_key.pub
It is also possible to sort files based on the time they were modified. You can do this by using the
-t
option.
The
-t
option will list the most recently modified files first. This option can be used alone, but again, is usually more helpful when paired with the -l
option:sysadmin@localhost:~$ ls -tl /etc/sshtotal 160-rw------- 1 root root 668 Jan 29 2015 ssh_host_dsa_key-rw-r--r-- 1 root root 607 Jan 29 2015 ssh_host_dsa_key.pub-rw-r--r-- 1 root root 179 Jan 29 2015 ssh_host_ecdsa_key.pub-rw------- 1 root root 227 Jan 29 2015 ssh_host_ecdsa_key -rw------- 1 root root 1675 Jan 29 2015 ssh_host_rsa_key-rw-r--r-- 1 root root 125749 Apr 29 2014 moduli-rw-r--r-- 1 root root 399 Jan 29 2015 ssh_host_rsa_key.pub -rw-r--r-- 1 root root 2489 Jan 29 2015 sshd_config -rw-r--r-- 1 root root 1669 Apr 29 2014 ssh_configsysadmin@localhost:~$-rw-r--r-- 1 root root 302 Jan 10 2011 ssh_import_id
It is important to remember that the modified date on directories represents the last time a file was added to or removed from the directory.
If the files in a directory were modified many days or months ago, it may be harder to tell exactly when they were modified, as only the date is provided for older files. For more detailed modification time information you can use the
--full-time
option to display the complete timestamp (including hours, seconds, minutes...):sysadmin@localhost:~$ ls -t --full-time /etc/sshtotal 160-rw------- 1 root root 668 2015-01-29 03:17:33.000000000 +0000 ssh_host_dsa_key-rw-r--r-- 1 root root 607 2015-01-29 03:17:33.000000000 +0000 ssh_host_dsa_key.pub-rw------- 1 root root 227 2015-01-29 03:17:33.000000000 +0000 ssh_host_ecdsa_key-rw------- 1 root root 1675 2015-01-29 03:17:33.000000000 +0000 ssh_host_rsa_key-rw-r--r-- 1 root root 179 2015-01-29 03:17:33.000000000 +0000 ssh_host_ecdsa_key.pub -rw-r--r-- 1 root root 399 2015-01-29 03:17:33.000000000 +0000 ssh_host_rsa_key.pub-rw-r--r-- 1 root root 302 2011-01-10 18:48:29.000000000 +0000 ssh_import_id-rw-r--r-- 1 root root 2489 2015-01-29 03:17:33.000000000 +0000 sshd_config -rw-r--r-- 1 root root 125749 2014-04-29 23:58:51.000000000 +0000 moduli-rw-r--r-- 1 root root 1669 2014-04-29 23:58:51.000000000 +0000 ssh_configsysadmin@localhost:~$
The
--full-time
option will assume the -l
option automatically.
It is possible to perform a reverse sort with either the
-S
or -t
options by using the -r
option. The following command will sort files by size, smallest to largest:sysadmin@localhost:~$ ls -lrS /etc/sshtotal 160-rw-r--r-- 1 root root 179 Jan 29 2015 ssh_host_ecdsa_key.pub-rw-r--r-- 1 root root 302 Jan 10 2011 ssh_import_id-rw------- 1 root root 227 Jan 29 2015 ssh_host_ecdsa_key -rw-r--r-- 1 root root 399 Jan 29 2015 ssh_host_rsa_key.pub-rw-r--r-- 1 root root 1669 Apr 29 2014 ssh_config-rw-r--r-- 1 root root 607 Jan 29 2015 ssh_host_dsa_key.pub -rw------- 1 root root 668 Jan 29 2015 ssh_host_dsa_key -rw------- 1 root root 1675 Jan 29 2015 ssh_host_rsa_keysysadmin@localhost:~$-rw-r--r-- 1 root root 2489 Jan 29 2015 sshd_config-rw-r--r-- 1 root root 125749 Apr 29 2014 moduli
The following command will list files by modification date, oldest to newest:
sysadmin@localhost:~$ ls -lrt /etc/sshtotal 160-rw-r--r-- 1 root root 302 Jan 10 2011 ssh_import_id-rw-r--r-- 1 root root 125749 Apr 29 2014 moduli-rw-r--r-- 1 root root 1669 Apr 29 2014 ssh_config -rw-r--r-- 1 root root 2489 Jan 29 2015 sshd_config-rw-r--r-- 1 root root 179 Jan 29 2015 ssh_host_ecdsa_key.pub-rw-r--r-- 1 root root 399 Jan 29 2015 ssh_host_rsa_key.pub -rw------- 1 root root 1675 Jan 29 2015 ssh_host_rsa_key -rw------- 1 root root 227 Jan 29 2015 ssh_host_ecdsa_keysysadmin@localhost:~$-rw-r--r-- 1 root root 607 Jan 29 2015 ssh_host_dsa_key.pub-rw------- 1 root root 668 Jan 29 2015 ssh_host_dsa_key
7 Listing With Globs
In a previous chapter, we discussed the use of file globs to match filenames using wildcard characters. For example, we demonstrated that you can list all of the files in the
/etc
directory that begin with the letter e
with the following command:sysadmin@localhost:~$ echo /etc/e*/etc/encript.cfg /etc/environment /etc/ethers /etc/event.d /etc/exportssysadmin@localhost:~$
Now that you know that the
ls
command is normally used to list files in a directory, using the echo
command may seem to have been a strange choice. However, there is something about the ls
command that might have caused confusion while we were discussing globs. This "feature" might also cause problems when you try to list files using glob patterns.
Keep in mind that it is the shell, not the
echo
or ls
command, that expands the glob pattern into corresponding file names. In other words, when you typed the echo /etc/e*
command, what the shell did before executing the echo
command was replace e*
with all of the files and directories within the /etc
directory that match the pattern.
So, if you were to run the
ls /etc/e*
command, what the shell would really run would be this:ls /etc/encript.cfg /etc/environment /etc/ethers /etc/event.d /etc/exports
When the
ls
command sees multiple arguments, it performs a list operation on each item separately. In other words, the command ls /etc/encript.cfg /etc/environment
is essentially the same as ls /etc/encript.cfg; ls /etc/environment
.
Now consider what happens when you run the
ls
command on a file, such as encript.cfg
:sysadmin@localhost:~$ ls /etc/enscript.cfg/etc/enscript.cfgsysadmin@localhost:~$
As you can see, running the
ls
command on a single file results in the name of the file being printed. Typically this is useful if you want to see details about a specific file by using the -l
option to the ls
command:sysadmin@localhost:~$ ls -l /etc/enscript.cfg-r--r--r--. 1 root root 4843 Nov 11 2010 /etc/enscript.cfgsysadmin@localhost:~$
However, what if the
ls
command is given a directory name as an argument? In this case, the output of the command is different than if the argument was a file name:sysadmin@localhost:~$ ls /etc/event.dck-log-system-restart ck-log-system-start ck-log-system-stopsysadmin@localhost:~$
If you give a directory name as an argument to the
ls
command, the command will display the contents of the directory (the names of the files in the directory), not just provide the directory name. The filenames you see in the example above are the names of the files in the /etc/event.d
directory.
Why is this a problem when using globs? Consider the following output:
sysadmin@localhost:~$ ls /etc/e*/etc/encript.cfg /etc/environment /etc/ethers /etc/event.d /etc/exports/etc/event.d:sysadmin@localhost:~$ck-log-system-restart ck-log-system-start ck-log-system-stop
As you can see, when the
ls
command sees a filename as an argument, it just displays the filename. However, for any directory, it will display the contents of the directory, not just the directory name.
This becomes even more confusing in a situation like the following:
sysadmin@localhost:~$ ls /etc/ev*ck-log-system-restart ck-log-system-start ck-log-system-stopsysadmin@localhost:~$
In the previous example, it seems like the
ls
command is just plain wrong. But what really happened is that the only thing that matches the glob /etc/ev*
is the /etc/event.d
directory. So, the ls
command only displayed the files in that directory!
There is a simple solution to this problem: when you use glob arguments with the
ls
command, always use the -d
option. When you use the -d
option, then the ls
command won't display the contents of a directory, but rather the name of the directory:sysadmin@localhost:~$ ls -d /etc/e*/etc/encript.cfg /etc/environment /etc/ethers /etc/event.d /etc/exportssysadmin@localhost:~$
0 comments