The /boot Directory Explained: vmlinuz, initramfs and the EFI Partition
/boot is small, mostly ignored, and the one directory whose failure stops the machine from starting at all. It is also the one that quietly fills up.
What is in there
ls -lh /boot
# vmlinuz-6.14.0-27-generic
# initrd.img-6.14.0-27-generic
# System.map-6.14.0-27-generic
# config-6.14.0-27-generic
# grub/
# efi/
vmlinuz-* is the compressed kernel image. The bootloader loads it into memory and jumps to it. The name is historical: vmlinux was the uncompressed kernel with virtual memory support, and the z marks the compressed form.
initrd.img-* or initramfs-* is a compressed archive containing a minimal userspace: the modules and tools needed to find and mount the real root filesystem. Our initramfs guide covers it in depth.
System.map-* maps kernel symbols to addresses. It is used when decoding an oops or panic, and is otherwise inert.
config-* is the configuration the kernel was built with. Useful for answering “is this feature compiled in”, which comes up more than you would expect.
# is a given option enabled in the running kernel
grep CONFIG_BTRFS_FS /boot/config-$(uname -r)
grub/ holds the bootloader’s own modules and grub.cfg, which is generated rather than edited. Our GRUB guide covers why editing it directly is the wrong move.
/boot/efi is a different thing entirely
This is the part that confuses people, and the distinction matters when something breaks.
findmnt /boot /boot/efi
# /boot /dev/nvme0n1p2 ext4
# /boot/efi /dev/nvme0n1p1 vfat
/boot is a normal Linux filesystem holding kernels and initramfs images.
/boot/efi is the EFI System Partition, mounted inside /boot by convention rather than necessity. It is FAT32, because the UEFI specification only guarantees that firmware can read FAT. The firmware has to load the bootloader before any operating system exists, so the filesystem has to be one the firmware understands natively.
ls /boot/efi/EFI/
# BOOT/ ubuntu/ Microsoft/
efibootmgr -v # what the firmware is configured to boot
Consequences of it being FAT:
- No Unix permissions. Everything appears as
rootwith fixed mode bits - No symlinks
- Case insensitive
- It is shared with other operating systems, which is why a Windows update can disturb your boot entries on a dual-boot machine
Our BIOS versus UEFI post covers why this partition exists at all.
The partition that fills up
This is the single most common /boot problem, and it fails in an unhelpful way.
df -h /boot
# /dev/nvme0n1p2 512M 498M 0 100% /boot
Every kernel version installs a vmlinuz and an initramfs. Initramfs images are large, frequently 50 to 100 MB each because they contain a broad set of modules. Distributions keep several versions deliberately, so you can boot an older kernel when a new one breaks.
On a separate /boot of 512 MB, that is roughly four or five kernels before it is full.
The failure mode is nasty: an update installs the new kernel, runs out of space generating the initramfs, and leaves the package system half-configured. Subsequent apt operations then fail until you sort it out.
Clearing it properly
# what is installed, and what you are running
dpkg --list | grep linux-image
uname -r
# Debian and Ubuntu
sudo apt autoremove --purge
# Fedora
sudo dnf remove --oldinstallonly
# or set a limit in /etc/dnf/dnf.conf
# installonly_limit=3
# Arch, if you use a hook
paccache -rk2
Go through the package manager, not rm. Deleting files directly leaves the package database believing those kernels are installed, and leaves bootloader entries pointing at files that no longer exist. That gives you a boot menu where some entries drop you into a panic.
Never remove the kernel you are currently running, which is what uname -r tells you.
If it is already full and apt is stuck:
# remove one old kernel's files to make room, then fix properly
sudo rm /boot/initrd.img-<old-version>
sudo apt --fix-broken install
sudo apt autoremove --purge
sudo update-grub
That is the exception, taken only to buy enough space for the package manager to work again.
When /boot is not a separate partition
Plenty of installs put /boot on the root filesystem, with only the ESP separate. That removes the fill-up problem entirely.
Separate /boot exists for reasons that still apply in some setups:
- Full disk encryption, where the bootloader needs an unencrypted kernel to start from, as in our encrypted installation guide
- Btrfs or ZFS roots with bootloaders that handle them poorly
- LVM or RAID roots on older setups
If you are hitting the size limit repeatedly and none of those apply, the real fix is moving /boot onto root, and that is an install-time decision rather than something to attempt on a running system.
Regenerating things when they break
# rebuild the initramfs for the current kernel
sudo update-initramfs -u # Debian and Ubuntu
sudo dracut --force # Fedora and RHEL
sudo mkinitcpio -P # Arch
# rebuild for all installed kernels
sudo update-initramfs -u -k all
# regenerate the boot menu
sudo update-grub
sudo grub2-mkconfig -o /boot/grub2/grub.cfg # Fedora
A missing or corrupt initramfs produces a panic about being unable to mount the root filesystem. Our kernel panic guide covers reading the message, and chroot rescue covers regenerating it from live media.
systemd-boot keeps things elsewhere
On systems using systemd-boot rather than GRUB, the layout differs: kernels and initramfs images usually live on the ESP itself, under /boot or /efi, with entries in loader/entries/.
bootctl status
ls /boot/loader/entries/
That makes the ESP size the constraint, and a 100 MB ESP created by a Windows installer is then far too small. 512 MB or 1 GB is the sensible size when you are partitioning yourself, as covered in our partitioning guide.
A quick health check
# space
df -h /boot /boot/efi
# do the kernels and initramfs images pair up
ls /boot/vmlinuz-* | wc -l
ls /boot/initr* | wc -l
# does the firmware know how to boot this machine
efibootmgr -v
# is anything in the menu pointing at a missing file
grep -o '/boot/vmlinuz[^ ]*' /boot/grub/grub.cfg | sort -u | while read -r f; do
[ -e "$f" ] || echo "MISSING: $f"
done
Mismatched counts mean an interrupted update. A menu entry pointing at a missing file means someone deleted kernels by hand, and update-grub fixes the menu once the packages are consistent.
Frequently Asked Questions
What is vmlinuz and why is it named that?
It is the compressed Linux kernel image. The name is historical: vmlinux was the uncompressed kernel with virtual memory support, and the z on the end marks the compressed form. Your bootloader loads this file and hands control to it.
Why does my /boot partition keep filling up?
Because each kernel version installs a vmlinuz and an initramfs, and initramfs images are large. Distributions keep several versions so you can boot an older one if a new kernel fails, and on a small separate /boot those copies add up until an update fails partway through.
Is it safe to delete old kernels from /boot manually?
Remove them through the package manager rather than with rm, because deleting the files leaves the package database thinking they are installed and leaves bootloader entries pointing at nothing. Use apt autoremove or dnf remove-old-kernels, and never remove the kernel you are currently running.
What is the difference between /boot and /boot/efi?
They are separate filesystems. /boot holds kernels and initramfs images and is usually ext4. /boot/efi is the EFI System Partition, is FAT32 because the firmware can only read FAT, and holds the bootloader binaries the firmware itself executes.
Why is the EFI partition formatted as FAT32?
Because the UEFI specification requires firmware to support FAT, and nothing else is guaranteed. The firmware has to read the bootloader before any operating system is running, so the filesystem must be one it understands natively. That also means it has no Unix permissions.
Can I boot without an initramfs?
Yes, if the kernel has every driver needed to reach the root filesystem built in rather than as a module. Custom kernels are sometimes built this way. Distribution kernels are modular by design, so they require an initramfs, and a corrupt or missing one produces a kernel panic about being unable to mount root.