FAT32 Files
A FAT32 partition becomes useful when the disk program can turn a path into a directory entry, find the first cluster of a file, follow the FAT, and print the file bytes on the UART console.
A directory is not a folder icon. It is a file full of records. Each record either names another directory or points at the first cluster of data.
Goal
Add a read-only cat command to the disk program. The test file lives below a subdirectory on
the FAT32 boot partition: /ALQ/HELLO.TXT. The command must mount the first FAT32 partition,
walk the path component by component, find the directory entry for the file, read its cluster chain, and
print the file on the UART console.
cat
cat /ALQ/HELLO.TXT
disk cat /ALQ/HELLO.TXT
Directories Are Files
FAT32 directories are stored in ordinary clusters. Their data is an array of 32-byte entries. A directory entry can describe a regular file, a subdirectory, a volume label, a deleted slot, the end of the used directory area, or part of a long filename. There is no tree object hidden elsewhere. The tree is built by reading one directory file, finding a directory entry inside it, and then reading the cluster chain named by that entry.
root directory cluster
ALQ directory, first_cluster=...
HELLO.TXT regular file, first_cluster=..., size=...
Short Names
The original FAT directory name is the 8.3 short name: eight bytes for the base name and three bytes for
the extension. The bytes are padded with spaces. HELLO.TXT is stored as HELLO TXT.
A short-name entry also contains the attribute byte, timestamps, the high and low halves of the first
cluster number, and the file size in bytes.
offset size meaning
0 8 short base name
8 3 short extension
11 1 attributes
20 2 first cluster high word
26 2 first cluster low word
28 4 file size in bytes
Long Names
Long filenames are stored as special entries immediately before the real short-name entry. Each long-name
slot has attribute 0x0F and carries up to thirteen UTF-16 code units. The slots appear on disk
in reverse order, so the reader collects pieces until it reaches the real file entry, then uses the assembled
long name for matching and display. The program also keeps the 8.3 fallback, because simple test files and
firmware-created names often do not need long-name slots at all.
Walking a Path
A path is a sequence of names separated by slashes. To resolve /ALQ/HELLO.TXT, the disk program
starts in the FAT32 root directory cluster, searches for ALQ, checks that it is a directory,
then searches inside that directory for HELLO.TXT. The final entry must be a regular file.
directory_cluster = root_cluster
find "ALQ" in directory_cluster
if entry is directory: directory_cluster = entry.first_cluster
find "HELLO.TXT" in directory_cluster
if entry is file: read entry.first_cluster for entry.size bytes
Reading File Data
FAT32 stores file data in clusters. The directory entry gives only the first cluster and the byte size. To
continue past the first cluster, the reader indexes the FAT. Each FAT entry says which cluster comes next.
Values at or above 0x0FFFFFF8 mark the end of the chain. This lesson reads at most a small
bounded amount so a mistaken file cannot flood the console.
cluster_lba = data_lba + (cluster - 2) * sectors_per_cluster
fat_offset = cluster * 4
next_cluster = FAT[fat_offset] & 0x0FFFFFFF
The Code Change
The disk task now accepts a file request. The shell remains responsive because cat only posts
work to the disk task. The FAT32 code has a reusable mount step, a directory lookup routine that understands
long names and 8.3 names, a path resolver for subdirectories, and a bounded file printer.
> cat /ALQ/HELLO.TXT
cat: requested /ALQ/HELLO.TXT
> cat: initializing disk
cat: path /ALQ/HELLO.TXT
File HELLO.TXT: first_cluster=... size=... bytes
--- file begin ---
Hello from Alquist FAT32.
This file lives in /ALQ/HELLO.TXT.
--- file end ---
This is the first storage lesson where the disk path becomes visibly useful as a file reader: the user types
a path, the program resolves the directory entries, follows the cluster chain, and prints the file bytes back
to the console. The debug shell still exists for raw SD work, but the lesson itself uses the normal
dir and cat commands.
Prepare the Card
Boot Linux on the Raspberry Pi once, mount the FAT32 boot partition, create the subdirectory, and copy a small text file there:
sudo mkdir -p /boot/firmware/ALQ
printf 'Hello from Alquist FAT32.\nThis file lives in /ALQ/HELLO.TXT.\n' | sudo tee /boot/firmware/ALQ/HELLO.TXT
sync
Then install the bare-metal image again and boot it from the SD card. The program remains read-only; Linux creates the test directory and file, Alquist only reads them.
Try It
make
make test-mbr
On hardware, run:
help
tasks
led toggle
dir
cat
cat /ALQ/HELLO.TXT
tasks
The dir command should show the ALQ subdirectory in the FAT32 root. The cat
command should print the file contents and return to the prompt while the scheduler heartbeat continues.
Next
The next storage step can turn this into a reusable file loader: choose a path, read a whole file into a caller-provided buffer, and hand that buffer to later kernel lessons that load programs from disk.