How to use lsof to view open files (on Linux everything is files)
October 18, 2021
If everything in Linux is a file, then there must be more to this operating system than just files on your hard drive. In this tutorial, you will learn how to use lsof to view all other devices and processes that are being treated as files.
Everything in Linux is files
The oft-quoted phrase that everything in Linux is a file is kind of true. A file is a collection of bytes. Programs and devices (printer, screen, keyboard, mouse, terminal, network card) can generate or receive streams of bytes, and in this capacity they themselves appear as files. Many system components such as keyboards, sockets, printers, and communications processes receive or generate streams of bytes. Because they accept, generate, or receive and generate streams of bytes, these devices can be treated – at a very low level – like files. In addition to ordinary files, files are also directories (folders), network sockets (network connections), devices (disks, terminals, keyboard, mouse, etc. – these are all files), pipe (a technology for exchanging data between processes).
This device concept has simplified the implementation of the Unix operating system. This meant that a small set of handlers, tools, and APIs could be built to handle a wide variety of different resources.
The data and program files that reside on your hard drive are regular files in the file system. We can use the ls command to list them and find out some details about them. But how do we know about all other processes and devices that are treated as files? The lsof command is used for this. It lists the open files on the system. That is, it lists everything that is processed as if it were a file.
lsof stands for “LiSt Open Files”. This program is used to find out which files are open and by which process.
Why do you need to know which files are open? This information will help you learn about a lot that is happening in the system, about the device and operation of Linux, and also solve problems, for example, when you cannot unmount the disk due to the device being in use, but you cannot find which program.
Many processes or devices that lsof can report are owned by root or were started by the root user, so you will need to use the sudo with lsof.
And since this list will be very long, you can pipe it to the less command:
sudo lsof | less
Before lsof output appears, users might see a warning message in a terminal window.
lsof: WARNING: can't stat() fuse.gvfsd-fuse file system /run/user/1000/gvfs Output information may be incomplete.
lsof tries to process all mounted filesystems. This warning message appears because lsof has detected the GNOME Virtual File System (GVFS). This is a special case of a user space filesystem (FUSE). It acts as a bridge between GNOME, its API, and the kernel. No one, not even root, can access one of these filesystems other than the owner who mounted it (in this case, the current user). You can ignore this warning. If you want to access this filesystem, then run lsof without sudo.
The lsof output header:
lsof column meaning
There are many types of open files, and not all columns apply to all of them. Therefore, if for some files some columns are not filled with data, then this is normal.
- COMMAND contains the first nine characters of the name of the UNIX command associated with the process.
- PID is the Process IDentification number of the process.
- TID is the task (thread) IDentification number, if task (thread) reporting is supported by the dialect and a task (thread) is being listed. A blank TID column in Linux indicates a process – i.e., a non-task.
- TASKCMD is the task command name. Generally this will be the same as the process named in the COMMAND column, but some task implementations (e.g., Linux) permit a task to change its command name.
- USER is the user ID number or login name of the user to whom the process belongs, usually the same as reported by ps. However, on Linux USER is the user ID number or login that owns the directory in /proc where lsof finds information about the process. Usually that is the same value reported by ps, but may differ when the process has changed its effective user ID.
- FD is the File Descriptor number of the file. File descriptors are described below.
- TYPE is the type of node associated with the file. The types of these types are described below.
- DEVICE contains the device numbers, separated by commas, for a character special, block special, regular, directory or NFS file.
- SIZE/OFF is the size of the file or the file offset in bytes.
- NODE is the node number of a local file; or the inode number of an NFS file in the server host; or the Internet protocol type - e.g, “TCP”; or “STR” for a stream; or “CCITT” for an HP-UX x.25 socket; or the IRQ or inode number of a Linux AX.25 socket device.
- NAME is the name of the mount point and file system on which the file resides. For other types of files, specific data is indicated here, details will be given below.
The file descriptor in the FD column can be one of many; the man page lists them all:
An entry in the FD column can have three parts: a file descriptor, a mode symbol, and a lock symbol.
Some popular file descriptors are:
- cwd: current working directory;
- err FD: information error (see NAME column);
- ltx: shared library text (code and data);
- m86: DOS Merge mapped file;
- mem: memory-mapped file;
- mmap: memory-mapped device;
- pd: parent directory;
- rtd: root directory;
- txt: program text (code and data);
The mode symbol can be one of the following:
- r: for read access;
- w: for write access;
- u: for read and write access;
- : [space character] if mode unknown and no lock character follows;
- -: if mode unknown and lock character follows.
The lock symbol can be one of:
- r: for read lock on part of the file;
- R: for a read lock on the entire file;
- w: for a write lock on part of the file;
- W: for a write lock on the entire file;
- u: for a read and write lock of any length;
- U: for a lock of unknown type;
- : [space character] if there is no lock.
More than 70 entries can be displayed in the TYPE column. The following are just a few of the commonly used entries:
- REG: Regular file system file.
- DIR: Directory.
- FIFO: for a FIFO (First In First Out) special file.
- CHR: Character special file.
- BLK: Block special file.
- INET: Internet socket.
- unix: UNIX domain socket.
- IPv4: IPv4 socket.
- IPv6: IPv6 files on the network – even if its IPv4 address is mapped to an IPv6 address.
- sock: Unknown domain socket.
- DEL: Linux pointer to remote file.
- LINK: A symbolic link file.
- PIPE: A pipe is a way of exchanging data between processes.
This field can be:
- the name of the mount point and file system on which the file resides;
- or the name of a file specified in the names option (after any symbolic links have been resolved);
- or the name of a character special or block special device;
- or the local and remote Internet addresses of a network file; the local host name or IP number is followed by a colon (':'), the port, “->”, and the two-part remote address; IP addresses may be reported as numbers or names, depending on the +|-M, -n, and -P options; colon-separated IPv6 numbers are enclosed in square brackets; IPv4 INADDR_ANY and IPv6 IN6_IS_ADDR_UNSPECIFIED addresses, and zero port numbers are represented by an asterisk ('*'); a UDP destination address may be followed by the amount of time elapsed since the last packet was sent to the destination; TCP, UDP and UDPLITE remote addresses may be followed by TCP/TPI information in parentheses - state (e.g., “(ESTABLISHED)”, “(Unbound)”), queue sizes, and window sizes (not all dialects) – in a fashion similar to what netstat reports; see the -T option description or the description of the TCP/TPI field in OUTPUT FOR OTHER PROGRAMS for more information on state, queue size, and window size;
- or the address or name of a UNIX domain socket, possibly including a stream clone device name, a file system object's path name, local and foreign kernel addresses, socket pair information, and a bound vnode address;
- or the local and remote mount point names of an NFS file;
- or “STR”, followed by the stream name;
- or a stream character device name, followed by “->” and the stream name or a list of stream module names, separated by “→”;
- or another value that is usually typical for certain operating systems.
How to see the processes that opened the file
To see the processes that opened a specific file, specify the filename as a parameter to lsof. For example, to see the processes that opened the file /dev/sda, use this command:
COMMAND PID USER FD TYPE DEVICE SIZE/OFF NODE NAME doublecmd 1982 mial cwd DIR 8,0 4096 32768001 /mnt/disk_d/Share
As you may know (and if you don’t, see the article “Linux directory structure. Important Linux files”), the file /dev/sda is a hard disk. The above command will help you find the process that prevents you from unmounting (detaching) the disk.
You can check which command is used to open regular files, for example:
COMMAND PID USER FD TYPE DEVICE SIZE/OFF NODE NAME soffice.b 3686 mial 92uW REG 259,2 19826 5390035 Documents/Linux.odt
You can see that the file is opened by the user mial, it is a regular file (REG) and that it is opened by the soffice.b application (actually the soffice.bin application, but the name was not written in full).
To display the full name, use the +c option, for example:
lsof +c 15 /home/mial/Вирус.odt
Similarly, you can check if executable files are open (running), for example, to check if the file /bin/bash is running:
sudo lsof /bin/bash
How to view all files opened in a specific directory
To see the files that were opened from a directory and the processes that opened them, pass the directory to lsof as a parameter. To do this, use the +D DIRECTORY option.
To see all files that are open in the /var/log/ directory, use this command:
sudo lsof +D /var/log/
lsof responds with a list of all open files in that directory.
To see all files that were opened from the /home directory, use the following command:
sudo lsof +D /home
Files that were opened from the /home directory. Please note that some columns do not fully fit the data.
How to show only regular files
To show regular files and directories and exclude all other kinds of files (devices, sockets, etc.), run the following command:
sudo lsof /
How to see files that are open with a specified program or command
The COMMAND column contains the name of the executable file that opened the file. To see the files that were opened by a particular process, use the -c COMMAND option. Note that you can specify more than one search query for lsof at the same time.
sudo lsof -c ssh -c systemd
lsof will list files that were opened by any of the processes provided on the command line.
How to view files opened by a specific user
To limit the display to files that were opened by a specific user, use the -u USER option. In this example, we will look at files that were opened by processes that are owned or run as mial.
sudo lsof -u mial
All files that were opened as user mial will be listed. They include files that were opened, for example, by the desktop environment, or simply as a result of mial login.
How to exclude files opened by a specific user
To exclude files that were opened by the user, use the ^ operator. Removing users from the list makes it easier to find the information you are interested in. You must use the -u option as before and add a ^ at the beginning of the username.
sudo lsof -u ^mial
Negation (searching for any values other than the ones listed) can be used with any options for which a value can be specified, that is, with usernames, command names, process IDs, folders, etc.
For example, to show all files that were open in the /home directory, but which are opened by processes not owned by mial:
sudo lsof +D /home -u ^mial
How to find files that are open by a specified process
To list the files that have been opened by a specific process, use the -p PROCESS parameter and specify the process ID as the parameter.
sudo lsof -p 9099
All files that were opened by the process ID you specified are listed for you.
How to find the IDs of the processes that opened the file
To see the IDs of the processes that opened a particular file, use the -t FILE option.
sudo lsof -t /usr/share/mime/mime.cache
The IDs of the process that opened the file are displayed in a simple list.
How to display the size of open files
Use the -s option to display the size:
To sort by size of regular files, run the following command:
lsof / -s | sort -rnk 7
How to find out which processes and how much memory they consume in the Buff/Cache area
Buffer/cache is used by virtual file systems and also to optimize disk read/write, that is, files that have already been read from disk are placed there for faster access.
The following command sorts open files by size – they are the ones that take up space in buffer/cache:
lsof -s | sort -rnk 7 | less
Buffer/cache consumes not so much the kernel as all sorts of browsers, office programs, graphical environments, programs with large logs, etc. That is, all programs that open many files and/or large files and keep them open.
How to combine lsof search terms (logical AND and OR)
Let's list the files that were opened by user mial and which are associated with systemd processes. We know we can provide more than one search item on the command line, so this should be easy.
sudo lsof -u mial -c systemd
Now let's take a look at the output of lsof. It doesn't look right; the output contains entries that were started by the root user.
This is not what we expected. What happened?
If you provide multiple search terms, lsof will return any file that matches the first search term or the second search term, and so on. In other words, it performs an OR lookup.
To have lsof perform an AND search, use the -a option. This means that only those files will be listed that match the first search query, the second search query, and so on.
Let's try this again and use the -a option.
sudo lsof -u mial -c systemd -a
Now each file in the list is a file that was opened by or on behalf of mial and associated with systemd.
Note that two conditions, one of which contains a negation (^), are treated as logical AND:
sudo lsof +D /home -u ^mial
But if a logical AND is required, then it is better to make it a rule to always use the -a option, since this makes the command more unambiguous:
sudo lsof +D /home -u ^mial -a
and in the case of adding a third search term, it will work as expected:
sudo lsof -u mial +D /home/mial -c^chromium -a
Updating lsof output automatically
To put lsof into repeat mode, we can use the +r SECONDS option or its -r SECONDS option. The repetition option can be applied in two ways: +r or -r. We also need to add the number of seconds that we want lsof to wait before updating the display.
Using the repeat option in any format causes lsof to display the results as usual, but adds a dotted line at the bottom of the screen. The program waits for the number of seconds specified on the command line and then updates the display with a new set of results.
With the -r option, this will continue until you press Ctrl+c. In +r format, the program will continue until an empty result is received, or until you press Ctrl+c.
sudo lsof -u mial -c ssh -a -r5
Notice the dotted line (=======) at the bottom of the list. It decouples each new display of data when the output is refreshed.
Displaying files associated with Internet connections
The -i option allows you to view files opened by processes associated with network and Internet connections.
sudo lsof -i
All files related to network and Internet connections are displayed.
If you don't want port numbers to be replaced with names (for example, http instead of 80), then add the -P option:
sudo lsof -i -P
Display files associated with Internet connections by process ID
To see files opened by Internet connections that are associated with a specific process ID, add the -p PID parameter and the -a parameter.
Here we are looking for files opened over the Internet or a network connection using process ID 606.
sudo lsof -i -a -p 606
Displaying files related to Internet connections and commands
We can use the -c COMMAND option to find files opened by specific processes. To find files that were opened over the Internet or network connections associated with the ssh process, use the following command:
lsof -i -a -c ssh
Displaying files related to Internet connections and ports
We can make lsof report on files that were opened over the Internet or network connections on a specific port. To do this, we use the symbol “:” followed by the port number.
Here we ask lsof to list files that were opened by a network or internet connection using port 22.
lsof -i :22
How to show sockets only for a specific protocol
We can ask lsof to show files that have been opened by processes associated with network and Internet connections that use a particular protocol. We can choose from TCP, UDP and SMTP. Let's use the TCP protocol and see what we get. If you are only interested in network connections on the TCP protocol or UDP protocol, then you can use the following commands:
lsof -i TCP # or: lsof -i UDP
Protocols can be written in both uppercase and lowercase letters:
sudo lsof -i tcp
How to find out which process or service is listening on a port
To find out which program is listening on a particular port, run a command like this:
lsof -i :PORT
For example, to see the process that opened port 80:
lsof -i :80
If you want to check the busyness of a port on a specific protocol (TCP or UDP), then specify the protocol of interest before the port number:
lsof -i TCP:22 # or: lsof -i UDP:53
How to view only IPv4 or IPv6 connections
IPv6 is the sixth and newest version of the IP protocol.
To list open files of network connections for IPv4 only, run the command:
sudo lsof -i 4
To show only open files of type IPv6 run:
sudo lsof -i 6
How to view network connections in a port range
If you need to see all running processes that opened TCP port files in the range 1-1024, then run the command:
lsof -i TCP:1-1024
In addition to the range of ports separated by a hyphen, you can specify several ports or their ranges separated by commas:
lsof -i TCP:1-1024,8000-9000,10000
How to see the network connections of a specific host
Each network connection has a source node and a destination, to see connections that refer only to a specific host, run a command like this:
lsof -i @HOST
For example, I want to view only network connections for a local machine named HackWare, then the command is as follows:
lsof -i @HackWare
If I want to see connections to the suip.biz site, then the command is:
lsof -i @suip.biz
As a host, you can specify not only the names of sites or hosts, but also the IP address.
Combination of network connection filters
You can use all filters at once in a command of the form:
lsof -i PROTOCOL@HOST:PORT
lsof -i TCP@suip.biz:1-4000
How to stop all activity of a specific user
Sometimes you need to kill all processes of a specific user. Below is the command that will close all processes of the user mial:
sudo kill -9 `lsof -t -u mial`
Search using regular expressions of programs that opened files
You can use regular expressions in lsof filters.
The following example will find all files opened by a process whose name consists of exactly four characters and the third character in the name is the letter “o”.
lsof -c /^..o.$/i
This example will find all files opened by a process whose name consists of exactly four characters:
lsof -c /^....$/i
lsof command basics
We have covered only the most popular examples of using the lsof command. You can find a huge documentation on this program with a description of all options in its man page:
- Full-text search in MS Word files and archives in Linux (83.9%)
- The in-memory file system - how to use tmpfs (60.5%)
- Instructions for using the file command (60.5%)
- How to find out which process is modifying a file (60.5%)
- How to find out when Linux was installed (60.5%)
- How to connect to digital TV from a computer in Linux (IPTV, DVB-IP and TVoIP) (RANDOM - 50%)