DEV Community

Cover image for Linux 7.4 Speeds Up FAT32 fallocate by Up to 265x by Removing a Six-Line While Loop
Joho no Todai
Joho no Todai

Posted on Originally published at joho-todai.com AI-assisted

Linux 7.4 Speeds Up FAT32 fallocate by Up to 265x by Removing a Six-Line While Loop

Linux 7.4 brings an orders-of-magnitude speedup to FAT32, still widely used on USB drives and SD cards, making disk space preallocation up to 265 times faster. At the heart of the change is the removal of a while loop—but why can changing just a few lines of code make such a difference?

Key points

  • What happened: The FAT driver's fallocate implementation replaces a while loop that handled one cluster at a time with bulk allocation, adding four lines and deleting six in fs/fat/file.c
  • Why 265x: On synchronous mounts, the FAT table was written to disk after every cluster allocation. Bulk allocation drastically reduces these sync operations, cutting 92.489 seconds to 0.348 seconds with 4,096-byte clusters and sixteen 16MiB files
  • Scope: The improvement is limited to fallocate's FALLOC_FL_KEEP_SIZE path and does not directly affect ordinary file copying. Preallocation on USB drives and SD cards, and synchronous mounts in embedded environments, are the main beneficiaries

Allocating one cluster at a time

Linux provides fallocate, a system call that preallocates disk space for a file. With the FALLOC_FL_KEEP_SIZE flag, it reserves disk space without changing the file's reported size. This reserves space ahead of later writes and is used for tasks such as database and virtual disk image creation.

The problem was that Linux's FAT driver repeated this operation one cluster at a time.

A cluster is the smallest unit FAT32 uses to manage disk space, with its size set during formatting (from 512 bytes to several tens of kilobytes). Allocating 256MiB for a file requires about 524,000 clusters when each cluster is 512 bytes. The previous implementation handled these clusters in a while loop that allocated them individually.

A patch posted on October 12, local time, by Matheus Alves de Almeida of Brazil's Federal University of Rio Grande do Sul removes this loop.

The core change adds four lines and deletes six in fs/fat/file.c. The while (nr_cluster-- > 0) loop called fat_add_clusters(inode, 1) individually; it is replaced with a single call to fat_add_clusters(inode, nr_cluster), passing the required number as an argument. The full series consists of three patches; the first two add support for multiple clusters to fat_add_clusters().

Why synchronous mounts get a 265x speedup

I confirmed that the patch's commit message includes detailed benchmarks measured on QEMU/KVM (virtio-blk, cache=none).

The largest improvement came when using fallocate on sixteen 16MiB files with 4,096-byte clusters on a synchronous mount. Processing time fell from 92.489 seconds to 0.348 seconds, a 265.4x speedup.

The reason improvements jump by orders of magnitude on synchronous mounts (the -o sync option) is clear: every cluster allocation caused a synchronous write of FAT table updates to disk. It would be surprising if more than 65,000 synchronous writes took the same time as a single synchronous write. The commit message succinctly explains the structure.

The improvement is especially large on synchronous mounts. The new code can batch FAT updates, eliminating the need to sync after each cluster allocation.

Asynchronous mounts also improve. Allocating 256MiB with 512-byte clusters was 13.2x faster (2.328 seconds→0.175 seconds), and even the case with the smallest improvement (128 files × 16KiB, asynchronous) recorded a 5.3x speedup. Reducing the number of metadata operations helps even without synchronous writes.

Figure omitted — see the original article

FAT32 is still in service

Seeing 265x and expecting FAT32 file copies to become 265 times faster would be premature. This improvement applies only to fallocate and its FALLOC_FL_KEEP_SIZE path. Ordinary file copies and writes (cp and dd) follow different paths and do not benefit directly.

Who benefits, then?

FAT32 is used on USB drives, SD cards, digital camera media, and the EFI system partitions of all UEFI machines. As a common-denominator filesystem readable and writable by Windows, macOS, and Linux alike, it remains in service in 2026. fallocate is a system call used internally for database preallocation, virtual disk image creation, and some backup tools. Embedded environments writing to slow flash media on synchronous mounts stand to benefit substantially.

FAT filesystem maintainer OGAWA Hirofumi added an Acked-by to all three patches. The patches were merged for Linux 7.4-rc1 on October 25, local time, through Andrew Morton's non-MM pull request.

The pull request contains 134 patches in total. Beyond the fallocate improvement, the FAT changes alone include fixes for overflow in data region calculations on 32-bit systems and for rolling back entries when file creation fails.

Removing just a few lines of a while loop cut processing time from a minute and a half to 0.3 seconds. An inefficiency untouched for years had kept spinning inside the code all along.


Originally published on Joho no Todai. The Japanese original is here.

Top comments (0)