Key Takeaways

  • Links in Linux are like shortcuts: references to a file that don’t duplicate it.
  • A symbolic link references by filename but breaks if its target moves.
  • A hard link references by a file’s inode which can be more robust but harder to understand.

On Linux, a link is like a shortcut to a file, giving you great power to decide how you organize your filesystem. But there are two types of link, and they are very different.

In Linux, a file has two parts: its name and its contents. A structure called an “inode” connects a filename with the data it contains. This inode also stores metadata about the file, like its owner, permissions, and date of last change.

A diagram showing a filename referencing an inode that contains data and metadata.
Remove Ads

A filename simply points, or “links,” to this inode structure. This means that more than one filename can refer to the same structure, i.e. the same underlying file.

The default type of link is a “hard link.” You can create a hard link to an existing file using the ln command in this form:

ln existing_file new_hard_link

You will now have two filenames pointing to the same inode. It’s important to understand that there really is only one file here, it just happens to have two filenames. So you can use either name (or path) to refer to the same file, and everything will stay synchronized.

Try it out, and you’ll see what’s going on. Start by copying a file as you normally would, using the cp command:

echo "hello world" > foo
cp foo bar
ls -li
cat foo bar

Passing the i option to ls instructs it to print each file’s inode number at the beginning of the line. Note that the new file has a distinct inode, but the same contents as the original.

A Linux terminal shows a file being copied and the details of both resulting files.
Remove Ads

Now create a hard link to the original file and compare it:

ln foo hum
ls -li
cat foo bar hum
A Linux terminal showing three files, two of which reference the same inode.

Note that the hard link has the same inode as the original file: 43458473. Both foo and hum point to the same underlying file. Also note the number in the 3rd column, just to the right of the permissions. For the original file (foo) and the hard link (hum), this reads “2,” but it’s “1” for the copy (bar). This number represents the total number of hard links to that file.

Redrawing the first diagram to represent the original file and its hard link gives:

A diagram showing two filenames sharing an inode.
Remove Ads

There isn’t any meaningful difference between the original file and the hard link. In fact, both are “links” in the Linux sense, and this is why there’s an unlink command that does the same job as rm to delete a file.

By listing the inode numbers, you can confirm that there really is only one actual file for the two filenames. If you’re still in any doubt, try changing the contents of either file:

echo "some new contents" > hum
cat foo
Changing the contents of a file in Linux changes it for every link to that file.

Symbolic links (symlinks) also allow you to refer to the same file in multiple locations. The difference is that, while hard links reference inodes, soft links reference other files by filename. You still use the ln command to create a symlink, but pass the -s (symbolic) flag too:

Remove Ads
ln -s existing_file new_soft_link

A symbolic link is a file in its own right; it has an inode with its own contents. But the contents of a symlink is nothing more than a filename, a reference to a separate file that the symlink should act as a proxy for. Metadata stored in the symlink’s inode explicitly marks it as a symbolic link, so any program that uses it will know to fetch the filename it points to instead.

Here’s an example:

ln -s foo baz
cat baz
ls -li
A Linux terminal showing a symlink which is colored pink and has an arrow pointing to the original file.

Note that this looks quite similar to the hard link case, but the output from ls is quite different. First, the symlink is marked with an “l” (link) at the very start of the permissions. But, even more usefully, the symlink’s filename is colored pink and followed with an arrow and the original filename.

The relationship between the symlink and the original file is something like this:

Remove Ads
A diagram showing a symbolic link that references a file.

When you create a symlink, you get to choose exactly how to reference the file it points to. The previous example just uses a plain filename which is a relative reference to a file in the same directory. But you can use any valid path, relative or absolute, for example:

ln -s foo sub/dir/baz
ln -s foo ../../baz
ln -s foo /tmp/baz

You may already have spotted a flaw here: what if the original file changes its name or location? In fact, what if the symlink file changes its location? Well, depending on which path type you’re using—relative or absolute—and depending on whether both files are moved or only one, you may be OK. But you’ll need to be careful.

One common use of symlinks is to manage installed software. For example, on my system, I have vim—the text editor—and vi, the older editor it evolved from. They’re installed like this:

Remove Ads
A macOS terminal showing the vi binary symlinked to vim.

With this setup, any script that uses vi will silently use vim instead.

Both types of links are good for filesystem management. You can use links to organize your files and directories, making them more accessible without wasting disk space. For example:

# Create a hard link to the apache log file in home directory
~ $ ln /var/log/apache2/access_log apache-log

# Create a soft link to a deeply-nested directory
~ $ ln -s ./work/acme/2024/10 current-work

Links can be very useful as a way of switching between different files without having to modify them. For example, imagine you have a configuration file, conf, that some piece of software uses. You can create multiple configurations, store them in separate files, then switch between them using links:

# Create two config files
config $ mv conf dark.conf
config $ cp dark.conf light.conf

# Use the dark config
config $ ln -s dark.conf conf

# Switch to the light config. Note -f to force overwrite of existing link.
config $ ln -fs light.conf conf

A soft link works until the file it points to is moved or renamed, then it becomes a broken link:

A terminal showing the effects of a broken symbolic link.
Remove Ads

For this reason, soft links often work best in a narrow scope, when a file and its link are in the same directory, for example.

Hard links don’t suffer from this problem; you can safely move them anywhere within the same filesystem. They suffer from a different problem, however. Some editors—and other programs that act on a file—create a copy of a file and rename it on save, for backup purposes. This behavior can break hard links, causing them to get out-of-sync and take up twice the disk space. You need to carefully check the programs you edit hard links with, to make sure they don’t do this.

If you’re linking to a directory, a soft link is your only option. Hard links simply don’t make much sense when it comes to directories, and would create more problems than they’d solve. Hard links also cannot be stored in a git repository.

On the command line, a hard link is the default, but GUIs—like Nautilus, for example—typically only support soft links. Even then, you’ll have to enable the option via Preferences:

Remove Ads
Enabling the Create Link setting in the Nautilus file manager on Linux.

The concept of a soft link is slightly easier to understand and, potentially, safer. Soft links are more visible, more popular, and are generally easier to understand.


Whichever type of link you use, the concept can take some time and practice to get your head around. But links are very powerful and popular, so you’ll feel the benefit of them. Make sure you use ls to keep track of links and try not to go overboard!