Explanation of Linux' Directory Hierarchy

Explanation of Linux' Directory Hierarchy

There are a lot of new people to Linux in this forum, and for those who want to dig deeper into the system it might be useful to get a basic understanding of the Linux Directory Structure.

Linux applies to the FHS - the File Hierarchy Standard.
Detailed information available here: FHS 2.3 Specification (FHS 3.0 is being worked on since 2004 ...)

Slogan of the FHS:
"The filesystem standard has been designed to be used by Unix distribution developers, package developers, and system implementors. However, it is primarily intended to be a reference and is not a tutorial on how to manage a Unix filesystem or directory hierarchy." - FHS Homepage

Note: this is a pragmatic guide - suggestions are always welcome

cd / ; ls ;
bin   dev  home  mnt  proc  run  tmp  var
boot  etc  lib   media  opt  root  sbin  usr

/

The root directory - which is owned by the superuser. This is the "starting point" of all other directories in the system.
Unix system have (as opposed to Windows systems) only this one starting point (in Windows you have multiple drive letters). Everything is found below the root directory, no exceptions.

However, this does not mean there aren't any other drives / partitions - in Linux there simply all mounted within the directory hierarchy (for more details on this check /dev ).
Thanks to @lukimya

/bin

This directory contains binaries (i.e. executables) shipped with the kernel by default (for example ls or grep). These are extremely important for the usage of the system. You should never ever change anything in here.

/sbin

Same as bin, however the execution of these binaries requires superuser-privileges.

/boot

This directory contains files necessary for the boot process, such as the boot loader, initial ramdisks etc.
Unless you really know what you're doing, you should never touch anything in here (especially on Embedded Devices this directory needs to be treated with extreme caution).

ls /boot;
grub/ initramfs-linux.img memtest86+/ vmlinuz-linux

/dev

Under this directory you'll find all kinds of (software and hardware) devices (e. g. /dev/sdx for access to storage devices, /dev/random for random numbers etc.). This directory can be very useful for direct access to low level media.

Drives / Partitions
In /dev you'll also find all your drives (HDD, SSD, USB, ...). They are named as storage device roman-letter arabic-digit. The roman letter corresponds to the physical position of the storage device, the arabic digit to the partition on the storage device.

/dev/sda1 -> first partition on the first storage device
/dev/sdc2 -> second partition on the third storage device

Check out:

lsblk # list block devices

/etc

This directories contains a lot of configuration files (e.g. /etc/fstab) and subdirectories for individual applications (e.g. /etc/nginx/...). When configuring / debugging applications you should definitely have a look in here.

/home

This directory contains the Home directories (i.e. home folders) of all users (except superuser). The individual subdirectories are owned by the corresponding users (e.g. /home/userx is owned by userx).
" ~/ " is an abreviation of the user directory.
Typically, the user directory holds the user's media (Pictures, Documents, Movies, Music et cetera), but also a lot of user-specific configuration files (e.g. for web browser). Most of the time these are hidden because they start with a dot (.). To view these directories, invoke the -A paramter when using ls:

ls ~/ -A
.bash_history .bashrc .config/ Downloads/ Movies/ Pictures/

/lib

Libraries for default binaries (in /bin and /sbin). Libraries are essentially frameworks - they provide easier access / support to other applications.

/mnt

Can be used as a directory for mounting other filesystems.

/media

Can be used for mounting removeable media. However most Desktop Enviroments auto-mount these devices under /run/user/media.

/proc

The Kernel directory. The kernel writes a lot of information to this directory (e.g. /proc/meminfo or /proc/uptime) - therfore it is very useful for obtaining direct and fresh information about the system (again: low-level).
It can also be used to give the kernel instructions (e.g. CPU Governors on some ARM devices).

/opt

Optional software packages (not installed via package manager, sometimes closed-source packages)

/root

Home directory of the superuser (usually not used, because you should not be logged in as superuser).

/run

Information about processes running since last boot (e.g. process-id-files PID or lock files)

ls /run
initramfs/ lock/ log/ mount/ network/ ssh.pid wpa_supplicant.pid

/tmp

Direct access to RAM. By creating a file here, you are directly using your temporary system memory (very high speed and now wear-out). Data will be flushed on reboot.

/var

This directory contains mostly variable files - such as application logs or cache (not in RAM).

/var/cache
Used for caching (temporarily storing) data on the PC. Commonly used by package managers ( such as APT or pacman ) to keep copies of the currently installed packages for backup purposes (e.g. in *.deb or *.rpm-format).

/var/games
Variable data owned by games in /usr - I guess on the inside we all just really want to play...

/var/lock
Symbolic link to /run/lock/

/var/run
Symbolic link to /run

/var/spool
Contains data which needs to be processed later on (e.g. print queues).

/var/tmp
Same as /tmp (direct access to RAM), however data will be restored after reboot.

/usr

This directory is actually an almost exact replica of /. It is the so-called Secondary hierarchy.
Most important subdirectories are:

cd /usr ; ls ;
bin  lib  local  sbin  share  src

/usr/bin
Contains almost all the packages / software installed on the system including applications provided by the Distribution (e.g. APT or pacman) and user-installed packages (installed via package manager).

/usr/sbin
Same as /usr/bin, however the execution of these binaries requires superuser-privileges.

/usr/lib
Libraries for applications in /usr/bin and /usr/sbin

/usr/local
Same as /usr but contains self-compiled packages (and their data). Tertiary hierarchy.

/usr/share
This directories holds architecture unspecific files, mostly documentation / manual pages (used by the 'man' application).

/usr/src
Source code for applications (e.g. linux kernel).


More in depth explanation and differentiation:
ArchLinux Wiki: https://wiki.archlinux.org/index.php/Arch_filesystem_hierarchy
The Linux Documentation Project: http://tldp.org/LDP/intro-linux/html/sect_03_01.html (Thanks to @jereman1)
Man-Page of hier: http://linux.die.net/man/7/hier

Different Distributions may change these directories (or their usage) to vayring degrees - however this should be a general overview which should almost always apply.

If you have a question about any of these directories, go ahead and ask! (no troubleshooting please)
If you want to clarify / change / correct any of the above categories, go ahead and tell me!


EDIT 2015-03-17 Further differentiation and added links
EDIT 2015-03-16: Improved layout

32 Likes

This was a great post I haven't found anything so concise anywhere else. Thank you very much.

I'd like to request some of the more interesting things like symbolic links and things of that nature.

Sure, sounds like a good idea since there are A LOT of symlinks / binding mounts in the Linux Directory Hierarchy.
However, it will be tricky to leave out all the Distribution specific features / settings.

Great guide! Especially for beginners (but also for everyone else) it is important to know how the file hierarchy works. This guide explains pretty good, well done.

I have a questions that popped up in my head though. Where should I place files that applications need to access as their own user? For example, I run a Subsonic server. On installation I believe subsonic created a directory in /var. Music files are now stored in /var/subsonic/music, but is that a correct location for it? Are there default locations for these situations?

Thank you!

I don't know how Subsonic works, but I'd assume it does the same thing as mpd (MusicPlayerDaemon):
The installation routine (which is being run as superuser) creates a user for the application, a directory (e.g. /var/mpd) and changes the ownership of the directory from root to mpd (with chown -R mpd /var/mpd).

When the daemon (i.e. server) is launched, it automatically creates a process owned by mpd, which can the access /var/mpd.
(Of course the process could also be owned by root the whole time, but that creates huge potential security leaks.)

But that still does not really answer my question. Do those music files belong their? As /var is for variable files. Music files won't normally get changed very often, so do they meed to be in /var or is a place somewhere else more logical?

Short answer yes. /var is used for a lot of stuff 'variable' doesnt necessarily mean always changing, normally server files will go in /var (or /srv on some distros),m since its a music server they probably felt that was an appropriate location.

If you want put it somewhere else. For my music files (i use mpd) I have them in /data/music-free and have them symlinked to /home//Music

1 Like

Great! Thank you for your explanation.

Very good and detailed one.

Very well done explanation Good Job!

Altough linux does not have drives like windows does you can still put the directories on different partitions. It is very common to have a seoarate partition for /boot and /home. Should you have to reinstall, by using the same username and password using the same /home your themes and application settings are in place. the only thing that are missing are the apps themselves. So here again, much more practical than Windowns.

I don't get it. If I have 1 physical Disk and i spilt it into 2 partitions does that mean I have to install software onto the partition with OS on it. Because installing everything into the same place will slow down the whole comp.
I also noticed that when i was installing programs through the terminal it didn't ask me where I want to install them.

To avoid that. In Windows I have SSD for OS and drivers only and I install all other software on HDD.
So is this not possible in Linux?

No (to the software on the OS partition question). For instance, you could mount a Windows C drive and be able to access it. Think of sticky notes - each have their own contents. You can put them on top of other sticky notes to have more space to write. (Or, you can have just one large sticky note, if you want to.)

That is basically how mounting drives works in Linux. Each partition has its own contents which you can mount to a directory and access. I have a media drive which has a folder music/ in it - I can mount it to /meta/ and then get to the music folder by /meta/music/.

(You should be careful about what you want to mount, though, because if something is OS-dependent, like /var/, that doesn't automount for whatever reason, you end up with an empty var directory with no software installed. You should also be careful about selecting to automount drives in your /etc/fstab, because if the drive is not accessible for whatever reason, it won't boot successfully in most cases. This can happen with NTFS partitions accessible by Windows, if you don't start Linux after Windows from reboot, because of the whole nasty hibernation issue they brought with Windows 8 and 10... I digress.)

Most software (that isn't portable) on Linux is installed in the /var/ directory*. When you install a distro, you simply have to define a separate partition that automatically mounts to /var/, so that when you boot your computer it knows where to find programs. It depends on your distro, but you will probably be able to install software to a different directory with your package manager. You may be able to copy and then automount, or just create a link to another folder. Creating a different /var/ partition is best, though it all depends on your situation.

If Steam is all you're worried about, Steam is entirely contained in your /home/ directory. If you create a separate partition for that, it will hold all your Steam library with it, instead of with the other software.

*or the /usr/bin/ directory... lol. I should read the guide I'm posting in.

Only thing I would add is for people having trouble visulizing the file system is to think of the directories as boxes.

Thanks for making this post. I was thinking of doing something similar but never had enough time to make it happen. Maybe I should quit my job and become a full time poster on these forums. lol

I'm still confused like Idiot. I would have to see a visual representation of this.

I don't understand the example with sticky notes.

The only thing i understood is that If I have more empty drives or partitions and I mount them to the /var/ directory. The destination path will not change but things will be physically installed in those empty drives/partitions and not to the OS drive/partition. Is that correct?

Mounting settings are lost when system is rebooted in Windows. Do they persist in Linux?

This is the layout of my hierarchy in windows environment.

  • Disk 1 - SSD

               [ Partition 1, C: drive = 120GB, OS + Drivers]
  • Disk 2 - HDD

               [Partition 1, D: drive = 879GB, Movies, Videos, Music, Photos]
               [Partition 2, E: drive = 491GB, Games, Program Files, Installation Packages]
               [Partition 3, F: drive = 491GB, Back ups, Dokuments, Torrent files, VMs]

I don't want games, programs or anything else for that matter to go anywhere near the OS. Is it possible to have it like this in Linux?

I'll go backwards, since that will be hopefully easier to understand.

Only if you specify them to. In Linux, there is a file specifically to handle automounting at boot called /etc/fstab. In there, you can specify the drive, the mountpoint, and some optional parameters.

You don't have to handle this yourself, of course. There are programs that will do what you want them to do. I'll mostly be talking about this from a terminal standpoint, because that's honestly the most straightforward way to solve problems in Linux sometimes.

Yeah. "Physically installed" not a very good term to use, so let me explain a little bit.

If you have a piece of software at /usr/bin/program, you can move that somewhere else (say, /home/user/program), link to it (ln -s /usr/bin/program /home/user/program), you can still reach it by going to /user/bin/program, or you can go to your home directory and it will be there. In theory, it's exactly like using shortcuts in Windows, though with the way Windows manages directories and partitions it seems like it's not as powerful as it is.

Now, if you moved it to your home directory and linked to it from there, the program would still work, even though it's in your home directory. Anything else that uses that piece of software thinks it's still at /usr/bin/program.

That said, software isn't really permanently installed anywhere. You can move it if you want to (if you have the right permissions), you can put links where you want to. I had problems with Bioshock: Infinite in my home directory (xfs problems), so I moved it to my /opt directory (my root dir is btrfs) and linked to it from the steam folder. It worked, and Steam thought it was still in there.

Mounting is like that - it just mounts for the base directory of that partition.

All hard drives and partitions get their own identification in /dev/sdx0.

For example, you would have this equivalent partition setup in Linux:

/dev/sda1: /
/dev/sdb1: /media
/dev/sdb2: /usr
/dev/sdb3: /home

I hope some of this sticks. I'm basically just throwing stuff out there at this point, lol. Does this make any more sense?

3 Likes

Yeah i understand it better now. But how can you have /user/ inside /home folder when usr is one of the top directories on the SSD?

dev = device i presume but what does sda1 and sdb1,2,3 means?

/home/user/ and /usr/ are unrelated. 'user' is just a placeholder name for your account name. For instance, mine would be /home/Jeol/. If you made your username 'home', you would have /home/home/ (it still works fine). It doesn't really matter.

Sorry, I should have explained that a little better. The letter refers to the actual drive, and the number refers to the partition. If you look at your drives in your computer, it is ordered by SATAs 1-6 (or however many it has), then USB drives. I don't know about PCI or M.2 drives, but they would probably come first. The partition number is whatever ID it is assigned by the drive. Assuming your SSD comes first, you have:

/dev/sda1
/dev/sdb1
/dev/sdb2
/dev/sdb3

If you plugged in a flash drive, you would get

/dev/sdc1
[...]

If you need to check, you can do a quick check using ls /dev/sd*. If it says '/dev/sdx' with no number assigned to it, it's the actual drive device itself. You can also use lsblk to learn some information.

NAME            MAJ:MIN RM   SIZE RO TYPE MOUNTPOINT
sda               8:0    0 465.8G  0 disk 
├─sda1            8:1    0   512M  0 part 
└─sda2            8:2    0 200.2G  0 part 
  ├─fedora-root 254:0    0  24.4G  0 lvm  
  └─fedora-home 254:1    0 146.5G  0 lvm  
sdb               8:16   0 931.5G  0 disk 
└─sdb1            8:17   0 867.5G  0 part /meta
sdc               8:32   0 447.1G  0 disk 
├─sdc1            8:33   0   500M  0 part 
├─sdc2            8:34   0    64G  0 part 
├─sdc5            8:37   0 238.4M  0 part /boot/efi
├─sdc6            8:38   0    61G  0 part /
└─sdc7            8:39   0    83G  0 part /home

That's the output I get from lsblk. /dev/sdc is actually my OS drive, though I do have /dev/sdb1 as my media partition. You can also see that the drive numbers aren't necessarily sequential. That's because I had a Windows install that I deleted, after I had already installed Linux from partitions 5-7.

1 Like

This is hands-down the clearest explanation I've come across on this topic. As a linux newbie, I thank you greatly for posting this <3

1 Like