File vs inode vs pathname vs symlink¶
Mental model¶
An inode is the actual file. A pathname is a name pointing to it. A file can have many names. A symlink is a separate file whose content is a pathname string.
What it looks like¶
"Delete the file." "Rename the file." "Link to the file." We say "file" to mean the name, the content, and the metadata all at once — but they're separate things.
What it really is¶
- Inode: the actual file object on disk. Contains metadata (permissions, ownership, timestamps, size) and pointers to data blocks. Identified by an inode number. Has no name.
- Pathname: a directory entry (dentry) that maps a name to an inode number. This mapping is called a hard link.
- Hard link: another pathname pointing to the same inode. The inode tracks a link count. All hard links are equal — there is no "original."
- Symlink (soft link): a separate inode whose data content is a pathname string. The filesystem follows the string to resolve the target. If the target pathname is removed, the symlink breaks.
Why it seems confusing¶
The word "file" collapses three concepts: the name you type, the metadata the kernel tracks, and the bytes on disk. Renaming a "file" only changes the directory entry — the inode (and its data) stays the same. "Deleting a file" really means removing a directory entry and decrementing the link count.
What actually matters¶
rmremoves a pathname (directory entry), not data. Data is freed when the link count reaches 0 AND no process holds the file open.- Hard links cannot cross filesystem boundaries (inodes are per-filesystem). Symlinks can.
- Hard links cannot point to directories (to prevent cycles).
mvwithin the same filesystem is just a directory entry rename — no data copy. Across filesystems it copies + unlinks.- An open file descriptor holds a reference to the inode, not the pathname. Deleting the pathname while a process has the file open: process keeps reading/writing, disk space freed when process closes the fd.
Common mistakes¶
- Thinking hard links are like shortcuts. They're equal names for the same inode — no "source" or "destination."
- Expecting
rmto free disk space immediately. If a process holds the file open, space isn't reclaimed until it closes. - Creating symlinks with relative paths and then moving them. The relative path resolves from the symlink's location.
- Confusing link count with reference count. Link count is pathnames; open file descriptors add references but not links.
Small examples¶
# Inode inspection
ls -i /etc/hostname # shows inode number
stat /etc/hostname # full inode metadata + link count
# Hard links
echo "data" > /tmp/a
ln /tmp/a /tmp/b # second pathname, same inode
ls -i /tmp/a /tmp/b # same inode number
stat /tmp/a | grep Links # Links: 2
rm /tmp/a # link count drops to 1
cat /tmp/b # still works — inode intact
# Symlinks
ln -s /tmp/b /tmp/c # new inode, content = "/tmp/b"
ls -l /tmp/c # shows -> /tmp/b
rm /tmp/b # target gone
cat /tmp/c # error: broken symlink
ls -i /tmp/c # different inode from original
One-line summary¶
Inode = the file (no name); pathname = a name for an inode; symlink = a file containing a pathname string.